Skip to content

push member journey page#9

Merged
SimonBurmer merged 10 commits intomainfrom
member-journey-pr
Mar 31, 2026
Merged

push member journey page#9
SimonBurmer merged 10 commits intomainfrom
member-journey-pr

Conversation

@ValentinAhrend
Copy link
Copy Markdown
Contributor

@ValentinAhrend ValentinAhrend commented Mar 8, 2026

  • inserted new START Munich media content
  • less lovable feel
  • mindmap dependencies
  • white background / UI changes

Summary by CodeRabbit

  • New Features

    • Dynamic network logos API and Member Network integration with grouped categories, loading/error states, and logo tiles.
    • New Join Start 2026 page; Apply page now redirects there.
  • UI/UX

    • Revamped Member Journey (desktop mindmap, mobile fallback), faster auto-rotate carousel, hover-driven previews, keyboard-accessible event rows, and updated imagery.
    • Simplified Community navigation and unified “Apply Now” CTAs to the new route.
  • Style

    • Added stroked text and animated dashed-line CSS utilities.
  • Chores

    • Added TypeScript incremental build info.

@vercel
Copy link
Copy Markdown

vercel Bot commented Mar 8, 2026

The latest updates on your projects. Learn more about Vercel for GitHub.

Project Deployment Actions Updated (UTC)
start-munich Ready Ready Preview, Comment Mar 31, 2026 0:41am
website-special-pages-y5ch Ready Ready Preview, Comment Mar 31, 2026 0:41am

Copy link
Copy Markdown

Copilot AI left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Pull request overview

This PR updates the member-facing experience by redesigning the Member Journey page (new layout, internal events UI, alumni section, CTA visuals) and making the Member Network page data-driven via a new /api/network-logos endpoint backed by NocoDB.

Changes:

  • Redesign app/member-journey/page.tsx with a new timeline layout, department “mindmap”, revamped internal events section, alumni testimonials, and new CTA visuals.
  • Add a new API route app/api/network-logos/route.ts and update app/member-network/page.tsx to fetch/render categorized logos.
  • Add new public assets (CTA SVGs + Cambridge aerial image) and supporting global CSS for the new visuals/animations.

Reviewed changes

Copilot reviewed 5 out of 16 changed files in this pull request and generated 6 comments.

Show a summary per file
File Description
public/cta-right.svg Adds decorative CTA SVG asset.
public/cta-left.svg Adds decorative CTA SVG asset.
public/cambridge-aerial.webp Adds Cambridge aerial image used on Member Journey page.
components/Navigation.tsx Simplifies community submenu items by removing arrow icon markup.
app/member-network/page.tsx Fetches network logos from new API and renders grouped logo grid with next/image.
app/member-journey/page.tsx Major UI rewrite: new timeline cards, mindmap departments, internal events UI, alumni cards, CTA visuals.
app/globals.css Adds .outline-text-dark and mindmap line dash animation styling.
app/api/network-logos/route.ts New endpoint fetching and transforming NocoDB records into UI-friendly logo objects.

Comment thread app/member-journey/page.tsx Outdated
Comment thread app/member-journey/page.tsx Outdated
Comment thread app/api/network-logos/route.ts Outdated
Comment thread app/api/network-logos/route.ts Outdated
Comment thread app/api/network-logos/route.ts Outdated
Comment thread app/member-journey/page.tsx Outdated
{(() => {
// Finops, Events, Marketing, Partnerships, People
// Arc: left, center-left, center, center-right, right
const positions: React.CSSProperties[] = [
Copy link

Copilot AI Mar 9, 2026

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

React.CSSProperties is used here, but React isn't imported in this file, so TypeScript will fail with "Cannot find namespace 'React'". Import type CSSProperties from react (or import React) and type positions as CSSProperties[] instead.

Copilot uses AI. Check for mistakes.
@coderabbitai
Copy link
Copy Markdown

coderabbitai Bot commented Mar 28, 2026

Note

Reviews paused

It looks like this branch is under active development. To avoid overwhelming you with review comments due to an influx of new commits, CodeRabbit has automatically paused this review. You can configure this behavior by changing the reviews.auto_review.auto_pause_after_reviewed_commits setting.

Use the following commands to manage reviews:

  • @coderabbitai resume to resume automatic reviews.
  • @coderabbitai review to trigger a single review.

Use the checkboxes below for quick actions:

  • ▶️ Resume reviews
  • 🔍 Trigger review
📝 Walkthrough

Walkthrough

Adds a dynamic Next.js API route to fetch/transform network logos from NocoDB; introduces CSS utilities for outlined text and animated dashed SVG lines; updates member-journey and member-network to use dynamic logos and revised assets/behaviors; adjusts navigation and several CTAs; adds a redirect page and TypeScript build cache.

Changes

Cohort / File(s) Summary
Network Logos API
app/api/network-logos/route.ts
New dynamic GET route reading NOCODB_API_TOKEN and NOCODB_NETWORK_LOGOS_TABLE_ID, fetching up to 1000 records from NocoDB (xc-token, cache: 'no-store'), transforming attachments to logoUrl (prefer signedPathpathurl, fallback ui-avatars), returns NetworkLogo[], logs samples in non-prod, and returns 500 JSON on errors.
Member Network page
app/member-network/page.tsx
Replaces previous company model with client-side fetch from /api/network-logos, adds loading/error/empty states, groups logos by category, renders logos via next/image (no prior image-fallback wrapper), and updates layout/styling.
Member Journey page
app/member-journey/page.tsx
Swapped many asset sources (local + external), renamed memberStoriesalumniTestimonials, removed scroll progress/ScrollIndicator, changed auto-rotate to 3s with hover pause, replaced departments grid with desktop SVG mindmap + mobile fallback, added keyboard accessibility, adjusted image behaviors and removed global fade/swap styles.
CSS Utilities
app/globals.css
Added .outline-text-dark stroked text utility, .mindmap-line dashed SVG stroke utility, and @keyframes dashFlow to animate dash offset.
Navigation & CTAs / Redirects
components/Navigation.tsx, app/apply/page.tsx, app/join-start/2026/page.tsx, app/members/page.tsx, app/startups/page.tsx
Removed some decorative arrow wrappers in Community dropdown; removed desktop/mobile “Member Network” link; changed multiple “Apply Now” links to internal /join-start/2026; added redirect page at app/apply/page.tsx and new landing page at app/join-start/2026/page.tsx.
Build Metadata
tsconfig.tsbuildinfo
Added TypeScript incremental build info file (compiler options, file list, hashes) — build cache artifact.

Sequence Diagram

sequenceDiagram
    participant Browser as Browser/Client
    participant MemberPage as MemberNetworkPage
    participant APIRoute as /api/network-logos
    participant NocoDB as NocoDB API

    Browser->>MemberPage: Request page
    MemberPage->>MemberPage: set loading state
    MemberPage->>APIRoute: GET /api/network-logos
    APIRoute->>APIRoute: read env (NOCODB_API_TOKEN, TABLE_ID)
    APIRoute->>NocoDB: fetch ?limit=1000 (header: xc-token)
    NocoDB-->>APIRoute: 200 OK + records
    APIRoute->>APIRoute: transform records -> NetworkLogo[] (extract signedPath/path/url or ui-avatars fallback)
    APIRoute-->>MemberPage: 200 JSON NetworkLogo[]
    MemberPage->>MemberPage: group by category, update state (loading=false)
    MemberPage->>Browser: render categorized logo sections (images)
Loading

Estimated code review effort

🎯 4 (Complex) | ⏱️ ~45 minutes

Possibly related PRs

  • Feat/member network #31: Similar changes to app/member-network and an API route for fetching network/logo data — likely the most directly related implementation.
  • Feat/UI improvements #10: Overlapping edits to components/Navigation.tsx removing/adjusting the Member Network navigation entry.
  • Feat: Add images #25: Related updates to app/member-journey/page.tsx that adjust event image assets and timeline behaviors.

Poem

🐰 I hopped through code and found a link,
Logos fetched from NocoDB in a blink,
Dashed mindmap lines that shimmer and wink,
Pages now local, images fixed in sync,
A happy rabbit twitches—quick! 🎉

🚥 Pre-merge checks | ✅ 1 | ❌ 2

❌ Failed checks (1 warning, 1 inconclusive)

Check name Status Explanation Resolution
Docstring Coverage ⚠️ Warning Docstring coverage is 0.00% which is insufficient. The required threshold is 80.00%. Write docstrings for the functions missing them to satisfy the coverage threshold.
Title check ❓ Inconclusive The title 'push member journey page' is vague and generic, using non-descriptive language that does not convey meaningful information about the substantial changes in this PR. Consider a more descriptive title that captures the main changes, such as 'Redesign member journey page with mindmap layout and updated network logos' or similar.
✅ Passed checks (1 passed)
Check name Status Explanation
Description Check ✅ Passed Check skipped - CodeRabbit’s high-level summary is enabled.

✏️ Tip: You can configure your own custom pre-merge checks in the settings.

✨ Finishing Touches
✨ Simplify code
  • Create PR with simplified code
  • Commit simplified code in branch member-journey-pr

Comment @coderabbitai help to get the list of available commands and usage tips.

Copy link
Copy Markdown

@coderabbitai coderabbitai Bot left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Actionable comments posted: 3

Caution

Some comments are outside the diff and can’t be posted inline due to platform limitations.

⚠️ Outside diff range comments (1)
app/member-journey/page.tsx (1)

37-37: ⚠️ Potential issue | 🔴 Critical

Fix case-sensitive image path to prevent 404 errors on production.

The code references /internalevents.png (lowercase i), but the actual file is Internalevents.png (capital I). Linux filesystems are case-sensitive, so this will fail to load on production.

Update line 37:

-const placeholderImage = "/internalevents.png"
+const placeholderImage = "/Internalevents.png"

Also update the onError handlers at lines 598 and 616 to use the correct case.

🤖 Prompt for AI Agents
Verify each finding against the current code and only fix it if needed.

In `@app/member-journey/page.tsx` at line 37, The image path is using the wrong
case causing 404s on case-sensitive filesystems: update the const
placeholderImage definition (placeholderImage) to reference
"/Internalevents.png" (capital I) and also update the two image onError handlers
that fall back to the placeholder (the onError callbacks used near the image
render code) to use the same "/Internalevents.png" value so all occurrences
consistently reference the correctly-cased filename.
🧹 Nitpick comments (6)
app/member-network/page.tsx (1)

8-8: export const dynamic has no effect in client components.

Since this file uses "use client", the dynamic export is ignored. This directive only affects Server Components and Route Handlers. The client-side fetch in useEffect already ensures dynamic behavior.

🔧 Proposed fix - remove unused export
 "use client"

 import { useState, useEffect } from "react"
 import Script from "next/script"
 import Image from "next/image"
 import Hero from "@/components/Hero"

-export const dynamic = 'force-dynamic'
-
 interface NetworkLogo {
🤖 Prompt for AI Agents
Verify each finding against the current code and only fix it if needed.

In `@app/member-network/page.tsx` at line 8, Remove the unused Server Component
directive by deleting the exported constant "dynamic" (export const dynamic =
'force-dynamic') from the client component in this file; since the file is
marked "use client" the dynamic export has no effect and can be removed to avoid
confusion and dead code — locate the export named dynamic in this module
(page.tsx) and remove it.
app/api/network-logos/route.ts (1)

54-64: Hardcoded limit of 1000 records may be insufficient.

If the network logos table grows beyond 1000 entries, logos will be silently truncated. Consider implementing pagination or documenting this limitation.

🤖 Prompt for AI Agents
Verify each finding against the current code and only fix it if needed.

In `@app/api/network-logos/route.ts` around lines 54 - 64, The fetch call that
queries
`${NOCODB_BASE_URL}/api/v2/tables/${NOCODB_NETWORK_LOGOS_TABLE_ID}/records?limit=1000&offset=0`
hardcodes limit=1000 which will truncate results if the table grows; update the
handler in route.ts to implement pagination (iterate with offset and limit until
fewer than limit records returned) or accept a query param to page through
results, using the same fetch call pattern (NOCODB_BASE_URL,
NOCODB_NETWORK_LOGOS_TABLE_ID) repeatedly and concatenating records before
returning; alternatively document the 1000-record limitation if pagination is
not desired.
app/globals.css (1)

106-114: Rename dashFlow to dash-flow for kebab-case consistency.

Stylelint flagged that keyframe names should follow kebab-case convention.

🔧 Proposed fix
 .mindmap-line {
   stroke-dasharray: 12 8;
-  animation: dashFlow 1s linear infinite;
+  animation: dash-flow 1s linear infinite;
 }

-@keyframes dashFlow {
+@keyframes dash-flow {
   0% { stroke-dashoffset: 20; }
   100% { stroke-dashoffset: 0; }
 }
🤖 Prompt for AI Agents
Verify each finding against the current code and only fix it if needed.

In `@app/globals.css` around lines 106 - 114, Rename the keyframes identifier from
"dashFlow" to kebab-case "dash-flow" and update any references: change the
`@keyframes` declaration name and the animation usage on .mindmap-line (animation:
dashFlow 1s linear infinite) to animation: dash-flow 1s linear infinite; ensure
the stroke-dashoffset keyframes remain the same and search for any other
occurrences of "dashFlow" to update them as well.
app/member-journey/page.tsx (2)

251-259: Unused navigation functions handlePrevImg and handleNextImg.

These functions are defined but never called in the JSX. If image navigation was intentionally removed, these should be cleaned up.

🧹 Remove unused code
-  const handlePrevImg = () => {
-    if (!activeImages || activeImages.length <= 1) return
-    setEventImgIdx(prev => (prev - 1 + activeImages.length) % activeImages.length)
-  }
-
-  const handleNextImg = () => {
-    if (!activeImages || activeImages.length <= 1) return
-    setEventImgIdx(prev => (prev + 1) % activeImages.length)
-  }
🤖 Prompt for AI Agents
Verify each finding against the current code and only fix it if needed.

In `@app/member-journey/page.tsx` around lines 251 - 259, handlePrevImg and
handleNextImg are defined but never used; either remove these unused functions
or hook them up to the image navigation UI. If you remove them, delete the
handlePrevImg and handleNextImg functions (and any related unused state like
setEventImgIdx only if it's truly unused). If you intend to keep navigation,
wire handlePrevImg and handleNextImg to the JSX navigation controls (e.g.,
prev/next buttons) so they call setEventImgIdx and use activeImages length as
already implemented. Ensure references to activeImages and setEventImgIdx remain
consistent with the existing state hooks when making the change.

7-7: export const dynamic has no effect in client components.

Same as member-network/page.tsx - this directive is ignored in "use client" files.

🔧 Proposed fix
 "use client"

 import { useState, useEffect, useRef, useCallback, type CSSProperties } from 'react'
 import Script from 'next/script'
 import Hero from "@/components/Hero"

-export const dynamic = 'force-dynamic'
-
 interface TimelineEvent {
🤖 Prompt for AI Agents
Verify each finding against the current code and only fix it if needed.

In `@app/member-journey/page.tsx` at line 7, The file exports a client-only
directive 'export const dynamic' which is ignored in components marked "use
client"; remove the redundant export (the 'export const dynamic' symbol) from
member-journey/page.tsx (same change as in member-network/page.tsx) or convert
the component to a server component if you need that dynamic behavior—ensure you
only keep 'export const dynamic' in true server components, not in files that
begin with "use client".
tsconfig.tsbuildinfo (1)

1-1: Add tsconfig.tsbuildinfo to .gitignore.

This auto-generated TypeScript incremental build metadata file should not be tracked in version control. It causes unnecessary merge conflicts and noisy diffs with each build, yet provides no benefit since TypeScript regenerates it automatically.

🤖 Prompt for AI Agents
Verify each finding against the current code and only fix it if needed.

In `@tsconfig.tsbuildinfo` at line 1, The repo is tracking the auto-generated
TypeScript incremental file tsconfig.tsbuildinfo; remove it from version control
and ignore future changes by adding tsconfig.tsbuildinfo to .gitignore and
running git rm --cached tsconfig.tsbuildinfo (then commit the updated .gitignore
and removal) so TypeScript can regenerate it locally without noisy diffs or
merge conflicts.
🤖 Prompt for all review comments with AI agents
Verify each finding against the current code and only fix it if needed.

Inline comments:
In `@app/api/network-logos/route.ts`:
- Around line 22-28: The constructed logoUrl can produce a double slash when
logo.signedPath or logo.path begins with '/', so change the concatenation in the
block that sets logoUrl (the branches referencing logo.signedPath, logo.path and
NOCODB_BASE_URL) to normalize the path first: either remove any leading slashes
from logo.signedPath/logo.path (e.g., trimLeft('/')/replace) before joining with
NOCODB_BASE_URL or build the URL with a proper URL join (e.g., new URL(path,
NOCODB_BASE_URL).toString()) to ensure a single slash between base and path.

In `@app/member-journey/page.tsx`:
- Around line 786-789: The "Apply Now" button in app/member-journey/page.tsx
currently has no action; add navigation behavior by turning the button into a
Next.js Link or attaching an onClick that routes to the application page (e.g.,
"/apply" or the correct route) so clicks navigate to the form; locate the JSX
for the button (the element with className "px-8 py-3 bg-brand-pink...") and
replace or wrap it with Link from 'next/link' or use useRouter().push inside an
onClick handler to perform the navigation.
- Line 378: Remove the duplicate conflicting Tailwind margin classes by editing
the JSX div that currently has className="space-y-3 mt-4 mt-0" (and the other
similar occurrence later) so only the intended margin-top remains (choose either
mt-0 or mt-4) — locate the div with className containing "space-y-3 mt-4 mt-0"
and remove the unwanted mt-* token to eliminate the merge artifact.

---

Outside diff comments:
In `@app/member-journey/page.tsx`:
- Line 37: The image path is using the wrong case causing 404s on case-sensitive
filesystems: update the const placeholderImage definition (placeholderImage) to
reference "/Internalevents.png" (capital I) and also update the two image
onError handlers that fall back to the placeholder (the onError callbacks used
near the image render code) to use the same "/Internalevents.png" value so all
occurrences consistently reference the correctly-cased filename.

---

Nitpick comments:
In `@app/api/network-logos/route.ts`:
- Around line 54-64: The fetch call that queries
`${NOCODB_BASE_URL}/api/v2/tables/${NOCODB_NETWORK_LOGOS_TABLE_ID}/records?limit=1000&offset=0`
hardcodes limit=1000 which will truncate results if the table grows; update the
handler in route.ts to implement pagination (iterate with offset and limit until
fewer than limit records returned) or accept a query param to page through
results, using the same fetch call pattern (NOCODB_BASE_URL,
NOCODB_NETWORK_LOGOS_TABLE_ID) repeatedly and concatenating records before
returning; alternatively document the 1000-record limitation if pagination is
not desired.

In `@app/globals.css`:
- Around line 106-114: Rename the keyframes identifier from "dashFlow" to
kebab-case "dash-flow" and update any references: change the `@keyframes`
declaration name and the animation usage on .mindmap-line (animation: dashFlow
1s linear infinite) to animation: dash-flow 1s linear infinite; ensure the
stroke-dashoffset keyframes remain the same and search for any other occurrences
of "dashFlow" to update them as well.

In `@app/member-journey/page.tsx`:
- Around line 251-259: handlePrevImg and handleNextImg are defined but never
used; either remove these unused functions or hook them up to the image
navigation UI. If you remove them, delete the handlePrevImg and handleNextImg
functions (and any related unused state like setEventImgIdx only if it's truly
unused). If you intend to keep navigation, wire handlePrevImg and handleNextImg
to the JSX navigation controls (e.g., prev/next buttons) so they call
setEventImgIdx and use activeImages length as already implemented. Ensure
references to activeImages and setEventImgIdx remain consistent with the
existing state hooks when making the change.
- Line 7: The file exports a client-only directive 'export const dynamic' which
is ignored in components marked "use client"; remove the redundant export (the
'export const dynamic' symbol) from member-journey/page.tsx (same change as in
member-network/page.tsx) or convert the component to a server component if you
need that dynamic behavior—ensure you only keep 'export const dynamic' in true
server components, not in files that begin with "use client".

In `@app/member-network/page.tsx`:
- Line 8: Remove the unused Server Component directive by deleting the exported
constant "dynamic" (export const dynamic = 'force-dynamic') from the client
component in this file; since the file is marked "use client" the dynamic export
has no effect and can be removed to avoid confusion and dead code — locate the
export named dynamic in this module (page.tsx) and remove it.

In `@tsconfig.tsbuildinfo`:
- Line 1: The repo is tracking the auto-generated TypeScript incremental file
tsconfig.tsbuildinfo; remove it from version control and ignore future changes
by adding tsconfig.tsbuildinfo to .gitignore and running git rm --cached
tsconfig.tsbuildinfo (then commit the updated .gitignore and removal) so
TypeScript can regenerate it locally without noisy diffs or merge conflicts.
🪄 Autofix (Beta)

Fix all unresolved CodeRabbit comments on this PR:

  • Push a commit to this branch (recommended)
  • Create a new PR with the fixes

ℹ️ Review info
⚙️ Run configuration

Configuration used: Organization UI

Review profile: CHILL

Plan: Pro

Run ID: 761ba0f1-f25a-4d08-ada4-898e3487d85a

📥 Commits

Reviewing files that changed from the base of the PR and between 568d460 and c29d08b.

⛔ Files ignored due to path filters (10)
  • public/cta-left.svg is excluded by !**/*.svg
  • public/cta-right.svg is excluded by !**/*.svg
  • public/member-journey-hero.jpg is excluded by !**/*.jpg
  • public/member-startup-visit.jpg is excluded by !**/*.jpg
  • public/member-workshops.png is excluded by !**/*.png
  • public/monthly-event.jpg is excluded by !**/*.jpg
  • public/more-dsc04524.jpg is excluded by !**/*.jpg
  • public/more-img4955.jpg is excluded by !**/*.jpg
  • public/more-isar-unfiltered.jpg is excluded by !**/*.jpg
  • public/more-workshops.png is excluded by !**/*.png
📒 Files selected for processing (7)
  • app/api/network-logos/route.ts
  • app/globals.css
  • app/member-journey/page.tsx
  • app/member-network/page.tsx
  • components/Navigation.tsx
  • public/cambridge-aerial.webp
  • tsconfig.tsbuildinfo

Comment thread app/api/network-logos/route.ts Outdated
Comment on lines +22 to +28
if (logo.signedPath) {
logoUrl = `${NOCODB_BASE_URL}/${logo.signedPath}`;
} else if (logo.path) {
logoUrl = `${NOCODB_BASE_URL}/${logo.path}`;
} else if (logo.url) {
logoUrl = logo.url;
}
Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

⚠️ Potential issue | 🟡 Minor

Potential double-slash in constructed logo URLs.

If logo.signedPath or logo.path already starts with /, the resulting URL will have a double slash (e.g., https://ndb.startmunich.de//path/to/logo).

🔧 Proposed fix
     if (record.Logo && Array.isArray(record.Logo) && record.Logo[0]) {
         const logo = record.Logo[0];
         if (logo.signedPath) {
-            logoUrl = `${NOCODB_BASE_URL}/${logo.signedPath}`;
+            logoUrl = `${NOCODB_BASE_URL}/${logo.signedPath.replace(/^\//, '')}`;
         } else if (logo.path) {
-            logoUrl = `${NOCODB_BASE_URL}/${logo.path}`;
+            logoUrl = `${NOCODB_BASE_URL}/${logo.path.replace(/^\//, '')}`;
         } else if (logo.url) {
             logoUrl = logo.url;
         }
     }
📝 Committable suggestion

‼️ IMPORTANT
Carefully review the code before committing. Ensure that it accurately replaces the highlighted code, contains no missing lines, and has no issues with indentation. Thoroughly test & benchmark the code to ensure it meets the requirements.

Suggested change
if (logo.signedPath) {
logoUrl = `${NOCODB_BASE_URL}/${logo.signedPath}`;
} else if (logo.path) {
logoUrl = `${NOCODB_BASE_URL}/${logo.path}`;
} else if (logo.url) {
logoUrl = logo.url;
}
if (logo.signedPath) {
logoUrl = `${NOCODB_BASE_URL}/${logo.signedPath.replace(/^\//, '')}`;
} else if (logo.path) {
logoUrl = `${NOCODB_BASE_URL}/${logo.path.replace(/^\//, '')}`;
} else if (logo.url) {
logoUrl = logo.url;
}
🤖 Prompt for AI Agents
Verify each finding against the current code and only fix it if needed.

In `@app/api/network-logos/route.ts` around lines 22 - 28, The constructed logoUrl
can produce a double slash when logo.signedPath or logo.path begins with '/', so
change the concatenation in the block that sets logoUrl (the branches
referencing logo.signedPath, logo.path and NOCODB_BASE_URL) to normalize the
path first: either remove any leading slashes from logo.signedPath/logo.path
(e.g., trimLeft('/')/replace) before joining with NOCODB_BASE_URL or build the
URL with a proper URL join (e.g., new URL(path, NOCODB_BASE_URL).toString()) to
ensure a single slash between base and path.

Comment thread app/member-journey/page.tsx Outdated
Comment thread app/member-journey/page.tsx Outdated
Copy link
Copy Markdown

@coderabbitai coderabbitai Bot left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Actionable comments posted: 3

Caution

Some comments are outside the diff and can’t be posted inline due to platform limitations.

⚠️ Outside diff range comments (1)
app/member-journey/page.tsx (1)

704-710: ⚠️ Potential issue | 🟡 Minor

Missing onError fallback for hovered event images.

The auto-rotating event images (line 751) and "more" images (line 690) have onError handlers, but hovered event images don't. This inconsistency could result in broken images.

🔧 Proposed fix
                     <img
                       key={eventImages[eventImageIndex]?.src}
                       src={eventImages[eventImageIndex]?.src}
                       alt={eventImages[eventImageIndex]?.title}
                       className="w-full h-full object-cover fade-swap"
+                      onError={(e) => { (e.target as HTMLImageElement).src = '/internalevents.png' }}
                     />
🤖 Prompt for AI Agents
Verify each finding against the current code and only fix it if needed.

In `@app/member-journey/page.tsx` around lines 704 - 710, Add an onError handler
to the hovered event image element (the <img> using
eventImages[eventImageIndex]?.src and key/title) to mirror the behavior used by
the auto-rotating and "more" images: call the same image error handler used
elsewhere (the handler used for auto-rotating/"more" images, e.g.,
handleImageError/onEventImageError) so the component replaces the broken src
with the fallback or marks the image as errored; this ensures the hovered image
(key eventImages[eventImageIndex]?.src, alt eventImages[eventImageIndex]?.title,
className "fade-swap") will not render broken images.
🧹 Nitpick comments (1)
app/member-journey/page.tsx (1)

543-576: Mindmap positions are tightly coupled to exactly 5 departments.

The hardcoded positions array has exactly 5 entries matching the current departments array. If departments are added or removed, this will silently fail or produce incorrect layouts.

💡 Consider adding a guard or generating positions dynamically
// Option 1: Add a runtime check
if (departments.length !== positions.length) {
  console.warn(`Mindmap positions (${positions.length}) don't match departments (${departments.length})`)
}

// Option 2: Or define positions alongside department data
🤖 Prompt for AI Agents
Verify each finding against the current code and only fix it if needed.

In `@app/member-journey/page.tsx` around lines 543 - 576, The positions array in
the block that renders departments (the const positions and its use in
departments.map) is hardcoded for exactly five items; add a safeguard and/or
dynamic position generation: check that departments.length equals
positions.length and log/warn (or fallback) if not, and preferably replace the
fixed const positions with a small helper (e.g., generatePositions(count) or
computeArcPositions) that returns an array of CSSProperties for any
departments.length and then use style={generatedPositions[i]} inside the
departments.map; update the rendering code to use the generated positions and
fall back to centered stacking if generation fails.
🤖 Prompt for all review comments with AI agents
Verify each finding against the current code and only fix it if needed.

Inline comments:
In `@app/globals.css`:
- Around line 100-114: Rename the keyframes identifier from dashFlow to
dash-flow to satisfy the keyframes-name-pattern rule and update the animation
reference in the .mindmap-line rule accordingly; specifically, rename the
`@keyframes` dashFlow declaration to `@keyframes` dash-flow and change the animation
property on .mindmap-line (animation: dashFlow 1s linear infinite) to use
dash-flow.

In `@app/member-journey/page.tsx`:
- Around line 581-602: The mobile department cards (rendered in the
departments.map loop inside the lg:hidden container) are missing padding causing
content to touch borders; update the outer card container element (the div with
className "relative bg-white/5 border border-white/10 overflow-hidden") used for
each dept to include the same padding as desktop (e.g., add p-5) so the dept
icon, name, description and responsibilities inside the map (dept, resp) have
consistent spacing.
- Around line 308-311: The updateScroll function can divide by zero when
scrollWidth === clientWidth; change updateScroll to compute a denominator =
scrollWidth - clientWidth and if denominator <= 0 set setScrollProgress(0) (or
clamp to 0) else compute setScrollProgress(scrollLeft / denominator), and
optionally clamp the result to [0,1]; reference the updateScroll function and
the variables scrollLeft, scrollWidth, clientWidth and setScrollProgress when
making the change.

---

Outside diff comments:
In `@app/member-journey/page.tsx`:
- Around line 704-710: Add an onError handler to the hovered event image element
(the <img> using eventImages[eventImageIndex]?.src and key/title) to mirror the
behavior used by the auto-rotating and "more" images: call the same image error
handler used elsewhere (the handler used for auto-rotating/"more" images, e.g.,
handleImageError/onEventImageError) so the component replaces the broken src
with the fallback or marks the image as errored; this ensures the hovered image
(key eventImages[eventImageIndex]?.src, alt eventImages[eventImageIndex]?.title,
className "fade-swap") will not render broken images.

---

Nitpick comments:
In `@app/member-journey/page.tsx`:
- Around line 543-576: The positions array in the block that renders departments
(the const positions and its use in departments.map) is hardcoded for exactly
five items; add a safeguard and/or dynamic position generation: check that
departments.length equals positions.length and log/warn (or fallback) if not,
and preferably replace the fixed const positions with a small helper (e.g.,
generatePositions(count) or computeArcPositions) that returns an array of
CSSProperties for any departments.length and then use
style={generatedPositions[i]} inside the departments.map; update the rendering
code to use the generated positions and fall back to centered stacking if
generation fails.
🪄 Autofix (Beta)

Fix all unresolved CodeRabbit comments on this PR:

  • Push a commit to this branch (recommended)
  • Create a new PR with the fixes

ℹ️ Review info
⚙️ Run configuration

Configuration used: Organization UI

Review profile: CHILL

Plan: Pro

Run ID: 2c648255-434d-4f57-ba13-ea5f5dc9665a

📥 Commits

Reviewing files that changed from the base of the PR and between c29d08b and 54f7432.

📒 Files selected for processing (4)
  • app/globals.css
  • app/member-journey/page.tsx
  • components/Navigation.tsx
  • tsconfig.tsbuildinfo
✅ Files skipped from review due to trivial changes (2)
  • components/Navigation.tsx
  • tsconfig.tsbuildinfo

Comment thread app/globals.css
Comment on lines +100 to +114
.outline-text-dark {
-webkit-text-stroke: 2px #00002c;
-webkit-text-fill-color: transparent;
paint-order: stroke fill;
}

.mindmap-line {
stroke-dasharray: 12 8;
animation: dashFlow 1s linear infinite;
}

@keyframes dashFlow {
0% { stroke-dashoffset: 20; }
100% { stroke-dashoffset: 0; }
}
Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

⚠️ Potential issue | 🟡 Minor

Keyframes name should use kebab-case per Stylelint rule.

The animation name dashFlow violates the keyframes-name-pattern rule. Rename to dash-flow for consistency.

🔧 Proposed fix
   .mindmap-line {
     stroke-dasharray: 12 8;
-    animation: dashFlow 1s linear infinite;
+    animation: dash-flow 1s linear infinite;
   }

-  `@keyframes` dashFlow {
+  `@keyframes` dash-flow {
     0% { stroke-dashoffset: 20; }
     100% { stroke-dashoffset: 0; }
   }
📝 Committable suggestion

‼️ IMPORTANT
Carefully review the code before committing. Ensure that it accurately replaces the highlighted code, contains no missing lines, and has no issues with indentation. Thoroughly test & benchmark the code to ensure it meets the requirements.

Suggested change
.outline-text-dark {
-webkit-text-stroke: 2px #00002c;
-webkit-text-fill-color: transparent;
paint-order: stroke fill;
}
.mindmap-line {
stroke-dasharray: 12 8;
animation: dashFlow 1s linear infinite;
}
@keyframes dashFlow {
0% { stroke-dashoffset: 20; }
100% { stroke-dashoffset: 0; }
}
.outline-text-dark {
-webkit-text-stroke: 2px `#00002c`;
-webkit-text-fill-color: transparent;
paint-order: stroke fill;
}
.mindmap-line {
stroke-dasharray: 12 8;
animation: dash-flow 1s linear infinite;
}
`@keyframes` dash-flow {
0% { stroke-dashoffset: 20; }
100% { stroke-dashoffset: 0; }
}
🧰 Tools
🪛 Stylelint (17.5.0)

[error] 111-111: Expected keyframe name "dashFlow" to be kebab-case (keyframes-name-pattern)

(keyframes-name-pattern)

🤖 Prompt for AI Agents
Verify each finding against the current code and only fix it if needed.

In `@app/globals.css` around lines 100 - 114, Rename the keyframes identifier from
dashFlow to dash-flow to satisfy the keyframes-name-pattern rule and update the
animation reference in the .mindmap-line rule accordingly; specifically, rename
the `@keyframes` dashFlow declaration to `@keyframes` dash-flow and change the
animation property on .mindmap-line (animation: dashFlow 1s linear infinite) to
use dash-flow.

Comment thread app/member-journey/page.tsx
Comment thread app/member-journey/page.tsx Outdated
Copy link
Copy Markdown

@coderabbitai coderabbitai Bot left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Caution

Some comments are outside the diff and can’t be posted inline due to platform limitations.

⚠️ Outside diff range comments (1)
app/member-journey/page.tsx (1)

705-711: ⚠️ Potential issue | 🟡 Minor

Missing onError fallback on hovered event image.

The hovered event image display lacks an onError handler, while the "moreImages" grid (line 691) and auto-rotating display (line 748) both have fallbacks. This inconsistency could result in broken images when hovering over events with failed image loads.

🔧 Proposed fix
                     <img
                       key={eventImages[eventImageIndex]?.src}
                       src={eventImages[eventImageIndex]?.src}
                       alt={eventImages[eventImageIndex]?.title}
                       className="w-full h-full object-cover fade-swap"
+                      onError={(e) => { (e.target as HTMLImageElement).src = '/internalevents.png' }}
                     />
🤖 Prompt for AI Agents
Verify each finding against the current code and only fix it if needed.

In `@app/member-journey/page.tsx` around lines 705 - 711, The hovered event image
at the <img> using eventImages[eventImageIndex] lacks an onError fallback; add
an onError handler to that <img> (the same one rendering
eventImages[eventImageIndex]?.src with className "fade-swap") that replaces the
failed src with the same fallback used by the "moreImages" grid and the
auto-rotating display (or a shared placeholder variable), and ensure the handler
avoids an infinite loop (e.g., only replace once or check current src before
swapping).
🧹 Nitpick comments (1)
app/member-journey/page.tsx (1)

505-505: Consider making mindmap height more responsive.

The fixed 900px height and -100px negative margin may cause layout issues on smaller desktop screens or if content changes. Consider using viewport-relative units or flexbox/grid for more robust sizing.

-              <div className="relative w-full" style={{ height: '900px', marginBottom: '-100px' }}>
+              <div className="relative w-full min-h-[700px] lg:min-h-[900px]" style={{ marginBottom: '-100px' }}>

Alternatively, investigate why the negative margin is needed—it often indicates a spacing issue that could be solved at a parent level.

🤖 Prompt for AI Agents
Verify each finding against the current code and only fix it if needed.

In `@app/member-journey/page.tsx` at line 505, The inline style on the div
rendered in page.tsx (the element with className "relative w-full") uses a fixed
height: '900px' and marginBottom: '-100px' which is brittle; replace the fixed
pixel height and negative margin with a responsive approach — e.g., use
minHeight or height in viewport units (like minHeight: '60vh' or height:
'70vh'), or switch the container to a flex or grid layout that lets the element
grow/shrink (adjust parent container styles instead of using negative margin),
and remove the negative margin once the parent spacing is fixed so the component
adapts on smaller screens.
🤖 Prompt for all review comments with AI agents
Verify each finding against the current code and only fix it if needed.

Outside diff comments:
In `@app/member-journey/page.tsx`:
- Around line 705-711: The hovered event image at the <img> using
eventImages[eventImageIndex] lacks an onError fallback; add an onError handler
to that <img> (the same one rendering eventImages[eventImageIndex]?.src with
className "fade-swap") that replaces the failed src with the same fallback used
by the "moreImages" grid and the auto-rotating display (or a shared placeholder
variable), and ensure the handler avoids an infinite loop (e.g., only replace
once or check current src before swapping).

---

Nitpick comments:
In `@app/member-journey/page.tsx`:
- Line 505: The inline style on the div rendered in page.tsx (the element with
className "relative w-full") uses a fixed height: '900px' and marginBottom:
'-100px' which is brittle; replace the fixed pixel height and negative margin
with a responsive approach — e.g., use minHeight or height in viewport units
(like minHeight: '60vh' or height: '70vh'), or switch the container to a flex or
grid layout that lets the element grow/shrink (adjust parent container styles
instead of using negative margin), and remove the negative margin once the
parent spacing is fixed so the component adapts on smaller screens.

ℹ️ Review info
⚙️ Run configuration

Configuration used: Organization UI

Review profile: CHILL

Plan: Pro

Run ID: ab043521-b2dd-4444-9a22-d4ff99dd5ffe

📥 Commits

Reviewing files that changed from the base of the PR and between 54f7432 and d5d733a.

📒 Files selected for processing (1)
  • app/member-journey/page.tsx

Copy link
Copy Markdown

@coderabbitai coderabbitai Bot left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

♻️ Duplicate comments (1)
app/member-journey/page.tsx (1)

559-580: ⚠️ Potential issue | 🟡 Minor

Mobile department cards are still missing padding.

The mobile fallback cards lack padding, causing content to touch the card borders. The desktop mindmap cards use p-5 (line 537), but the mobile version at line 563 doesn't have any padding applied.

🔧 Proposed fix
             <div className="lg:hidden space-y-4">
               {departments.map((dept) => (
                 <div
                   key={dept.id}
-                  className="relative bg-white/5 border border-white/10 overflow-hidden"
+                  className="relative bg-white/5 border border-white/10 overflow-hidden p-5"
                 >
🤖 Prompt for AI Agents
Verify each finding against the current code and only fix it if needed.

In `@app/member-journey/page.tsx` around lines 559 - 580, The mobile department
cards rendered in the departments.map callback (inside the "lg:hidden space-y-4"
block) are missing padding so content touches the card borders; update the card
container (the div keyed by dept.id with classes "relative bg-white/5 border
border-white/10 overflow-hidden") to include the same padding as desktop (e.g.,
add p-5) so the icon, title, description, and responsibility list have
consistent spacing; ensure you only modify that card div class string in the
component rendering departments so desktop behavior (lg:...) remains unchanged.
🧹 Nitpick comments (1)
app/member-journey/page.tsx (1)

682-688: Missing onError fallback for hovered event images.

The hovered event image (line 683-688) lacks an onError handler, unlike the "more" images (line 668) and auto-rotating images (line 707) which both fall back to /internalevents.png. This inconsistency could result in broken images if a local asset fails to load.

🔧 Proposed fix
                     <img
                       key={eventImages[eventImageIndex]?.src}
                       src={eventImages[eventImageIndex]?.src}
                       alt={eventImages[eventImageIndex]?.title}
                       className="w-full h-full object-cover fade-swap"
+                      onError={(e) => { (e.target as HTMLImageElement).src = '/internalevents.png' }}
                     />
🤖 Prompt for AI Agents
Verify each finding against the current code and only fix it if needed.

In `@app/member-journey/page.tsx` around lines 682 - 688, The hovered event image
img rendering using eventImages[eventImageIndex] is missing an onError fallback;
update the img element (the one using key={eventImages[eventImageIndex]?.src}
src={eventImages[eventImageIndex]?.src}
alt={eventImages[eventImageIndex]?.title} className="...fade-swap") to include
an onError handler that sets the image src to '/internalevents.png' (matching
the fallback used for the "more" images and auto-rotating images) and ensure it
guards against infinite loops by only replacing the src once.
🤖 Prompt for all review comments with AI agents
Verify each finding against the current code and only fix it if needed.

Duplicate comments:
In `@app/member-journey/page.tsx`:
- Around line 559-580: The mobile department cards rendered in the
departments.map callback (inside the "lg:hidden space-y-4" block) are missing
padding so content touches the card borders; update the card container (the div
keyed by dept.id with classes "relative bg-white/5 border border-white/10
overflow-hidden") to include the same padding as desktop (e.g., add p-5) so the
icon, title, description, and responsibility list have consistent spacing;
ensure you only modify that card div class string in the component rendering
departments so desktop behavior (lg:...) remains unchanged.

---

Nitpick comments:
In `@app/member-journey/page.tsx`:
- Around line 682-688: The hovered event image img rendering using
eventImages[eventImageIndex] is missing an onError fallback; update the img
element (the one using key={eventImages[eventImageIndex]?.src}
src={eventImages[eventImageIndex]?.src}
alt={eventImages[eventImageIndex]?.title} className="...fade-swap") to include
an onError handler that sets the image src to '/internalevents.png' (matching
the fallback used for the "more" images and auto-rotating images) and ensure it
guards against infinite loops by only replacing the src once.

ℹ️ Review info
⚙️ Run configuration

Configuration used: Organization UI

Review profile: CHILL

Plan: Pro

Run ID: 781bc720-04bc-4b79-a939-cf49ccf59d33

📥 Commits

Reviewing files that changed from the base of the PR and between d5d733a and 569e653.

⛔ Files ignored due to path filters (1)
  • public/Builder_Weekend.jpg is excluded by !**/*.jpg
📒 Files selected for processing (7)
  • app/apply/page.tsx
  • app/join-start/2026/page.tsx
  • app/member-journey/page.tsx
  • app/members/page.tsx
  • app/startups/page.tsx
  • components/Navigation.tsx
  • tsconfig.tsbuildinfo
✅ Files skipped from review due to trivial changes (3)
  • app/members/page.tsx
  • app/join-start/2026/page.tsx
  • tsconfig.tsbuildinfo
🚧 Files skipped from review as they are similar to previous changes (1)
  • components/Navigation.tsx

Copy link
Copy Markdown

@coderabbitai coderabbitai Bot left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Actionable comments posted: 3

♻️ Duplicate comments (3)
app/globals.css (1)

106-114: ⚠️ Potential issue | 🟡 Minor

Rename dashFlow to kebab-case to satisfy lint.

Line 108 and Line 111 still use dashFlow, which violates the configured keyframe naming rule and can fail stylelint.

🔧 Proposed fix
   .mindmap-line {
     stroke-dasharray: 12 8;
-    animation: dashFlow 1s linear infinite;
+    animation: dash-flow 1s linear infinite;
   }

-  `@keyframes` dashFlow {
+  `@keyframes` dash-flow {
     0% { stroke-dashoffset: 20; }
     100% { stroke-dashoffset: 0; }
   }
🤖 Prompt for AI Agents
Verify each finding against the current code and only fix it if needed.

In `@app/globals.css` around lines 106 - 114, The keyframe name dashFlow violates
the kebab-case rule; rename the keyframe to a kebab-case identifier (e.g.,
dash-flow) and update the .mindmap-line animation property to use the new name
so both the `@keyframes` rule and the animation reference match (update the
`@keyframes` declaration and the animation: dashFlow → animation: dash-flow in the
.mindmap-line rule).
app/api/network-logos/route.ts (1)

22-26: ⚠️ Potential issue | 🟡 Minor

Normalize attachment paths before joining URL base.

Line 23 and Line 25 can emit double slashes when incoming paths already start with /.

🔧 Proposed fix
         if (logo.signedPath) {
-            logoUrl = `${NOCODB_BASE_URL}/${logo.signedPath}`;
+            logoUrl = `${NOCODB_BASE_URL}/${String(logo.signedPath).replace(/^\/+/, '')}`;
         } else if (logo.path) {
-            logoUrl = `${NOCODB_BASE_URL}/${logo.path}`;
+            logoUrl = `${NOCODB_BASE_URL}/${String(logo.path).replace(/^\/+/, '')}`;
         } else if (logo.url) {
             logoUrl = logo.url;
         }
🤖 Prompt for AI Agents
Verify each finding against the current code and only fix it if needed.

In `@app/api/network-logos/route.ts` around lines 22 - 26, The URL concatenation
can produce double slashes when logo.signedPath or logo.path begins with a
leading slash; update the logic that builds logoUrl (the branches checking
logo.signedPath and logo.path which append to NOCODB_BASE_URL) to normalize the
attachment path first—strip any leading slashes (or use a URL/path-join helper)
before joining with NOCODB_BASE_URL so the resulting logoUrl is never formed
with "//" between base and path; leave the logo.url branch unchanged.
app/member-journey/page.tsx (1)

559-564: ⚠️ Potential issue | 🟡 Minor

Add padding to mobile department cards for consistent spacing.

On mobile, content sits against the border because the card wrapper lacks padding.

🔧 Proposed fix
-                  className="relative bg-white/5 border border-white/10 overflow-hidden"
+                  className="relative bg-white/5 border border-white/10 overflow-hidden p-5"

Based on learnings: Applies to **/*.{tsx,ts} : Implement responsive design.

🤖 Prompt for AI Agents
Verify each finding against the current code and only fix it if needed.

In `@app/member-journey/page.tsx` around lines 559 - 564, The mobile department
cards rendered in the departments.map loop (the element with className
"lg:hidden space-y-4" and each card div with className "relative bg-white/5
border border-white/10 overflow-hidden") lack inner padding; update the card
wrapper (the mapped div with key={dept.id}) to include responsive padding
classes (for example add "px-4 py-3" or "p-4 sm:p-6 lg:p-0") so that on small
screens the content has consistent spacing while preserving existing lg
behavior.
🧹 Nitpick comments (1)
app/member-network/page.tsx (1)

10-15: Avoid duplicating the NetworkLogo contract in client and API code.

This interface mirrors the API route shape exactly; keeping two copies increases drift risk. Consider moving it to a shared lib/types module and importing from there.

🤖 Prompt for AI Agents
Verify each finding against the current code and only fix it if needed.

In `@app/member-network/page.tsx` around lines 10 - 15, The interface NetworkLogo
is duplicated between client and API; extract NetworkLogo into a single shared
types module, export it, then replace the local interface declaration with an
import of NetworkLogo in both the client code (where it currently appears) and
the API route that uses the same shape; ensure the shared module is exported
correctly and update any imports/usages to reference the shared NetworkLogo type
to prevent drift.
🤖 Prompt for all review comments with AI agents
Verify each finding against the current code and only fix it if needed.

Inline comments:
In `@app/api/network-logos/route.ts`:
- Around line 55-64: The NocoDB fetch call (the request built with
NOCODB_BASE_URL, NOCODB_NETWORK_LOGOS_TABLE_ID and NOCODB_API_TOKEN) lacks an
abort/timeout and can hang; add an AbortController, pass its signal into the
fetch options, start a timer (e.g., using setTimeout) that calls
controller.abort() after a reasonable timeout (e.g., 5–10s), and clear the timer
when the fetch completes; ensure you catch the abort error and handle it (return
a 504 or appropriate error) so the route handler does not hang.

In `@app/member-journey/page.tsx`:
- Around line 683-688: The hovered-event image tag is missing an onError
fallback so broken URLs render a broken tile; update the <img> (the element
rendering eventImages[eventImageIndex]?.src with className "fade-swap") to
include an onError handler that replaces the image src with a known fallback
(e.g., a DEFAULT_EVENT_IMAGE or a safe placeholder URL) and removes or clears
the handler to avoid infinite loops; ensure you reference eventImages and
eventImageIndex in the handler so the fallback only applies to this renderer.

In `@app/member-network/page.tsx`:
- Around line 27-45: The code assumes the API response in fetchLogos is an array
and directly calls setLogos(data), which will make logos.reduce crash if the
payload is malformed; update fetchLogos to validate the payload before calling
setLogos by checking Array.isArray(data) (and optionally that each item matches
the expected NetworkLogo shape: has id/name/url/category) and if invalid log a
warning and call setLogos([]) or filter to a safe array; ensure the rest of the
component (grouped, logos.reduce) operates on this validated array so reduce
cannot throw.

---

Duplicate comments:
In `@app/api/network-logos/route.ts`:
- Around line 22-26: The URL concatenation can produce double slashes when
logo.signedPath or logo.path begins with a leading slash; update the logic that
builds logoUrl (the branches checking logo.signedPath and logo.path which append
to NOCODB_BASE_URL) to normalize the attachment path first—strip any leading
slashes (or use a URL/path-join helper) before joining with NOCODB_BASE_URL so
the resulting logoUrl is never formed with "//" between base and path; leave the
logo.url branch unchanged.

In `@app/globals.css`:
- Around line 106-114: The keyframe name dashFlow violates the kebab-case rule;
rename the keyframe to a kebab-case identifier (e.g., dash-flow) and update the
.mindmap-line animation property to use the new name so both the `@keyframes` rule
and the animation reference match (update the `@keyframes` declaration and the
animation: dashFlow → animation: dash-flow in the .mindmap-line rule).

In `@app/member-journey/page.tsx`:
- Around line 559-564: The mobile department cards rendered in the
departments.map loop (the element with className "lg:hidden space-y-4" and each
card div with className "relative bg-white/5 border border-white/10
overflow-hidden") lack inner padding; update the card wrapper (the mapped div
with key={dept.id}) to include responsive padding classes (for example add "px-4
py-3" or "p-4 sm:p-6 lg:p-0") so that on small screens the content has
consistent spacing while preserving existing lg behavior.

---

Nitpick comments:
In `@app/member-network/page.tsx`:
- Around line 10-15: The interface NetworkLogo is duplicated between client and
API; extract NetworkLogo into a single shared types module, export it, then
replace the local interface declaration with an import of NetworkLogo in both
the client code (where it currently appears) and the API route that uses the
same shape; ensure the shared module is exported correctly and update any
imports/usages to reference the shared NetworkLogo type to prevent drift.
🪄 Autofix (Beta)

Fix all unresolved CodeRabbit comments on this PR:

  • Push a commit to this branch (recommended)
  • Create a new PR with the fixes

ℹ️ Review info
⚙️ Run configuration

Configuration used: Organization UI

Review profile: CHILL

Plan: Pro

Run ID: 5b069433-9c81-4e7d-93f2-9722cb99e125

📥 Commits

Reviewing files that changed from the base of the PR and between 569e653 and b42a19f.

⛔ Files ignored due to path filters (11)
  • public/Builder_Weekend.jpg is excluded by !**/*.jpg
  • public/cta-left.svg is excluded by !**/*.svg
  • public/cta-right.svg is excluded by !**/*.svg
  • public/member-journey-hero.jpg is excluded by !**/*.jpg
  • public/member-startup-visit.jpg is excluded by !**/*.jpg
  • public/member-workshops.png is excluded by !**/*.png
  • public/monthly-event.jpg is excluded by !**/*.jpg
  • public/more-dsc04524.jpg is excluded by !**/*.jpg
  • public/more-img4955.jpg is excluded by !**/*.jpg
  • public/more-isar-unfiltered.jpg is excluded by !**/*.jpg
  • public/more-workshops.png is excluded by !**/*.png
📒 Files selected for processing (11)
  • app/api/network-logos/route.ts
  • app/apply/page.tsx
  • app/globals.css
  • app/join-start/2026/page.tsx
  • app/member-journey/page.tsx
  • app/member-network/page.tsx
  • app/members/page.tsx
  • app/startups/page.tsx
  • components/Navigation.tsx
  • public/cambridge-aerial.webp
  • tsconfig.tsbuildinfo
✅ Files skipped from review due to trivial changes (5)
  • app/join-start/2026/page.tsx
  • components/Navigation.tsx
  • app/members/page.tsx
  • app/apply/page.tsx
  • tsconfig.tsbuildinfo

Comment thread app/api/network-logos/route.ts Outdated
Comment on lines +55 to +64
const response = await fetch(
`${NOCODB_BASE_URL}/api/v2/tables/${NOCODB_NETWORK_LOGOS_TABLE_ID}/records?limit=1000&offset=0`,
{
headers: {
'xc-token': NOCODB_API_TOKEN,
'Content-Type': 'application/json',
},
cache: 'no-store',
}
);
Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

⚠️ Potential issue | 🟠 Major

Add a timeout to the NocoDB fetch to prevent hanging requests.

The current external call has no abort path. If NocoDB stalls, this route can hang until platform-level timeout.

⏱️ Proposed fix
-        const response = await fetch(
-            `${NOCODB_BASE_URL}/api/v2/tables/${NOCODB_NETWORK_LOGOS_TABLE_ID}/records?limit=1000&offset=0`,
-            {
-                headers: {
-                    'xc-token': NOCODB_API_TOKEN,
-                    'Content-Type': 'application/json',
-                },
-                cache: 'no-store',
-            }
-        );
+        const controller = new AbortController();
+        const timeout = setTimeout(() => controller.abort(), 8000);
+        const response = await fetch(
+            `${NOCODB_BASE_URL}/api/v2/tables/${NOCODB_NETWORK_LOGOS_TABLE_ID}/records?limit=1000&offset=0`,
+            {
+                headers: {
+                    'xc-token': NOCODB_API_TOKEN,
+                    'Content-Type': 'application/json',
+                },
+                cache: 'no-store',
+                signal: controller.signal,
+            }
+        );
+        clearTimeout(timeout);
📝 Committable suggestion

‼️ IMPORTANT
Carefully review the code before committing. Ensure that it accurately replaces the highlighted code, contains no missing lines, and has no issues with indentation. Thoroughly test & benchmark the code to ensure it meets the requirements.

Suggested change
const response = await fetch(
`${NOCODB_BASE_URL}/api/v2/tables/${NOCODB_NETWORK_LOGOS_TABLE_ID}/records?limit=1000&offset=0`,
{
headers: {
'xc-token': NOCODB_API_TOKEN,
'Content-Type': 'application/json',
},
cache: 'no-store',
}
);
const controller = new AbortController();
const timeout = setTimeout(() => controller.abort(), 8000);
const response = await fetch(
`${NOCODB_BASE_URL}/api/v2/tables/${NOCODB_NETWORK_LOGOS_TABLE_ID}/records?limit=1000&offset=0`,
{
headers: {
'xc-token': NOCODB_API_TOKEN,
'Content-Type': 'application/json',
},
cache: 'no-store',
signal: controller.signal,
}
);
clearTimeout(timeout);
🤖 Prompt for AI Agents
Verify each finding against the current code and only fix it if needed.

In `@app/api/network-logos/route.ts` around lines 55 - 64, The NocoDB fetch call
(the request built with NOCODB_BASE_URL, NOCODB_NETWORK_LOGOS_TABLE_ID and
NOCODB_API_TOKEN) lacks an abort/timeout and can hang; add an AbortController,
pass its signal into the fetch options, start a timer (e.g., using setTimeout)
that calls controller.abort() after a reasonable timeout (e.g., 5–10s), and
clear the timer when the fetch completes; ensure you catch the abort error and
handle it (return a 504 or appropriate error) so the route handler does not
hang.

Comment thread app/member-journey/page.tsx
Comment thread app/member-network/page.tsx Outdated
Comment on lines +27 to +45
const data = await res.json()
setLogos(data)
} catch (err) {
console.error("Error fetching network logos:", err)
setError("Failed to load network logos")
} finally {
setLoading(false)
}
}
fetchLogos()
}, [])

// Group by Type
const categories = Array.from(new Set(companies.map(c => c.type)))
.sort((a, b) => companies.filter(c => c.type === b).length - companies.filter(c => c.type === a).length)

if (loading) {
return (
<main className="min-h-screen bg-[#00002c] py-12 px-4 sm:px-6 lg:px-8">
<div className="max-w-7xl mx-auto text-center">
<p className="text-2xl font-bold text-white">Loading member network...</p>
</div>
</main>
)
}
// Group logos by category
const grouped = logos.reduce<Record<string, NetworkLogo[]>>((acc, logo) => {
const cat = logo.category || "Other"
if (!acc[cat]) acc[cat] = []
acc[cat].push(logo)
return acc
}, {})
Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

⚠️ Potential issue | 🟠 Major

Validate API payload shape before storing state.

Line 28 trusts res.json() as an array, but Line 40 requires an array (reduce). A malformed 200-response will crash rendering.

🛡️ Proposed fix
-        const data = await res.json()
-        setLogos(data)
+        const data: unknown = await res.json()
+        if (!Array.isArray(data)) {
+          throw new Error("Invalid network logos payload")
+        }
+        setLogos(data as NetworkLogo[])
📝 Committable suggestion

‼️ IMPORTANT
Carefully review the code before committing. Ensure that it accurately replaces the highlighted code, contains no missing lines, and has no issues with indentation. Thoroughly test & benchmark the code to ensure it meets the requirements.

Suggested change
const data = await res.json()
setLogos(data)
} catch (err) {
console.error("Error fetching network logos:", err)
setError("Failed to load network logos")
} finally {
setLoading(false)
}
}
fetchLogos()
}, [])
// Group by Type
const categories = Array.from(new Set(companies.map(c => c.type)))
.sort((a, b) => companies.filter(c => c.type === b).length - companies.filter(c => c.type === a).length)
if (loading) {
return (
<main className="min-h-screen bg-[#00002c] py-12 px-4 sm:px-6 lg:px-8">
<div className="max-w-7xl mx-auto text-center">
<p className="text-2xl font-bold text-white">Loading member network...</p>
</div>
</main>
)
}
// Group logos by category
const grouped = logos.reduce<Record<string, NetworkLogo[]>>((acc, logo) => {
const cat = logo.category || "Other"
if (!acc[cat]) acc[cat] = []
acc[cat].push(logo)
return acc
}, {})
const data: unknown = await res.json()
if (!Array.isArray(data)) {
throw new Error("Invalid network logos payload")
}
setLogos(data as NetworkLogo[])
} catch (err) {
console.error("Error fetching network logos:", err)
setError("Failed to load network logos")
} finally {
setLoading(false)
}
}
fetchLogos()
}, [])
// Group logos by category
const grouped = logos.reduce<Record<string, NetworkLogo[]>>((acc, logo) => {
const cat = logo.category || "Other"
if (!acc[cat]) acc[cat] = []
acc[cat].push(logo)
return acc
}, {})
🤖 Prompt for AI Agents
Verify each finding against the current code and only fix it if needed.

In `@app/member-network/page.tsx` around lines 27 - 45, The code assumes the API
response in fetchLogos is an array and directly calls setLogos(data), which will
make logos.reduce crash if the payload is malformed; update fetchLogos to
validate the payload before calling setLogos by checking Array.isArray(data)
(and optionally that each item matches the expected NetworkLogo shape: has
id/name/url/category) and if invalid log a warning and call setLogos([]) or
filter to a safe array; ensure the rest of the component (grouped, logos.reduce)
operates on this validated array so reduce cannot throw.

@SimonBurmer SimonBurmer merged commit 363d6d5 into main Mar 31, 2026
3 checks passed
@SimonBurmer SimonBurmer deleted the member-journey-pr branch April 4, 2026 23:32
@coderabbitai coderabbitai Bot mentioned this pull request Apr 7, 2026
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

3 participants