-
Notifications
You must be signed in to change notification settings - Fork 7
feat(header): show Layout switcher only in DEMO mode #451
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Conversation
The Layout combobox in the header is now only visible in DEMO mode. For deployed sites (non-DEMO), layout switching remains available only through Settings. - Add isDemoMode() condition in NavigationControls - Add isDemoMode() condition in mobile header - Layout switcher remains accessible via Settings in all modes
|
The latest updates on your projects. Learn more about Vercel for GitHub.
|
WalkthroughTwo header/navigation components were updated to add conditional demo mode checks. The Changes
Estimated code review effort🎯 2 (Simple) | ⏱️ ~5 minutes Possibly related PRs
Poem
Pre-merge checks and finishing touches❌ Failed checks (1 warning)
✅ Passed checks (2 passed)
✨ Finishing touches
🧪 Generate unit tests (beta)
Thanks for using CodeRabbit! It's free for OSS, and your support helps us grow. If you like it, consider giving us a shout-out. Comment |
Greptile SummaryThis PR restricts the Layout switcher visibility in the header navigation to DEMO mode only. The implementation adds Key Changes:
The changes are straightforward and correctly implement the feature requirement. The layout switcher functionality is preserved and simply hidden from the header UI when not in DEMO mode. Confidence Score: 5/5
Important Files Changed
Sequence DiagramsequenceDiagram
participant User
participant Header
participant NavigationControls
participant isDemoMode
participant LayoutSwitcher
User->>Header: Load page
Header->>isDemoMode: Check if DEMO mode
isDemoMode-->>Header: Returns boolean (NEXT_PUBLIC_DEMO === "true")
alt DEMO mode enabled
Header->>NavigationControls: Render navigation controls
NavigationControls->>isDemoMode: Check if DEMO mode
isDemoMode-->>NavigationControls: true
NavigationControls->>LayoutSwitcher: Render layout switcher (desktop)
LayoutSwitcher-->>User: Display layout switcher button
Header->>LayoutSwitcher: Render layout switcher (mobile menu)
LayoutSwitcher-->>User: Display layout switcher in mobile menu
else DEMO mode disabled
Header->>NavigationControls: Render navigation controls
NavigationControls->>isDemoMode: Check if DEMO mode
isDemoMode-->>NavigationControls: false
NavigationControls-->>User: Skip layout switcher rendering
Header->>isDemoMode: Check if DEMO mode
isDemoMode-->>Header: false
Header-->>User: Skip layout switcher in mobile menu
end
Note over User,LayoutSwitcher: Layout switcher remains available in Settings for all modes
|
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
No issues found across 2 files
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Actionable comments posted: 0
🧹 Nitpick comments (2)
components/header/index.tsx (1)
32-32: Consider memoizing the demo mode check.The implementation is correct, but since
process.env.NEXT_PUBLIC_DEMOis a build-time constant in Next.js, callingisDemoMode()on every render is unnecessary. Consider wrapping it inuseMemoto avoid redundant function calls.🔎 Optional optimization using useMemo
import { useMemo, useCallback, useState } from 'react'; import { useSession } from 'next-auth/react'; import { LayoutSwitcher } from '../layout-switcher'; import { NavigationControls } from '../navigation-controls'; import { ProfileButton } from './profile-button'; import { MoreMenu } from './more-menu'; import { SettingsButton } from '../settings-button'; import { Container } from '../ui/container'; import { SiteLogo } from '../shared/site-logo'; import { useFeatureFlagsWithSimulation } from '@/hooks/use-feature-flags-with-simulation'; import { useHasGlobalSurveys } from '@/hooks/use-has-global-surveys'; import { useCategoriesEnabled } from '@/hooks/use-categories-enabled'; import { useSurveysEnabled } from '@/hooks/use-surveys-enabled'; import { useTagsEnabled } from '@/hooks/use-tags-enabled'; import { useHeaderSettings } from '@/hooks/use-header-settings'; import { useCategoriesExists } from '@/hooks/use-categories-exists'; import { isDemoMode } from '@/lib/utils'; export default function Header() { const [isMenuOpen, setIsMenuOpen] = useState(false); const { data: session } = useSession(); const { features } = useFeatureFlagsWithSimulation(); const { hasGlobalSurveys, isPending: surveysPending } = useHasGlobalSurveys(); const { categoriesEnabled } = useCategoriesEnabled(); const { surveysEnabled } = useSurveysEnabled(); const { tagsEnabled } = useTagsEnabled(); const { settings: headerSettings } = useHeaderSettings(); const { data: categoriesData, isLoading: categoriesLoading } = useCategoriesExists(); - const isDemo = isDemoMode(); + const isDemo = useMemo(() => isDemoMode(), []);Alternatively, define it as a module-level constant outside the component:
+const IS_DEMO_MODE = isDemoMode(); + export default function Header() { const [isMenuOpen, setIsMenuOpen] = useState(false); const { data: session } = useSession(); const { features } = useFeatureFlagsWithSimulation(); const { hasGlobalSurveys, isPending: surveysPending } = useHasGlobalSurveys(); const { categoriesEnabled } = useCategoriesEnabled(); const { surveysEnabled } = useSurveysEnabled(); const { tagsEnabled } = useTagsEnabled(); const { settings: headerSettings } = useHeaderSettings(); const { data: categoriesData, isLoading: categoriesLoading } = useCategoriesExists(); - const isDemo = isDemoMode();Also applies to: 175-175
components/navigation-controls.tsx (1)
7-7: Consider memoizing the demo mode check (consistent with header component).Similar to the header component,
isDemoMode()is called on every render. Sinceprocess.env.NEXT_PUBLIC_DEMOis a build-time constant, consider usinguseMemoor a module-level constant for consistency and minor performance optimization.🔎 Optional optimization using useMemo
export function NavigationControls() { const { settings } = useHeaderSettings(); - const isDemo = isDemoMode(); + const isDemo = useMemo(() => isDemoMode(), []); return (Or define as a module-level constant:
+const IS_DEMO_MODE = isDemoMode(); + export function NavigationControls() { const { settings } = useHeaderSettings(); - const isDemo = isDemoMode(); + const isDemo = IS_DEMO_MODE;Also applies to: 11-11
📜 Review details
Configuration used: Organization UI
Review profile: CHILL
Plan: Pro
📒 Files selected for processing (2)
components/header/index.tsxcomponents/navigation-controls.tsx
🧰 Additional context used
📓 Path-based instructions (7)
**/*.{js,ts,tsx}
📄 CodeRabbit inference engine (.github/copilot-instructions.md)
Use Node.js >= 20.19.0
Files:
components/header/index.tsxcomponents/navigation-controls.tsx
components/**/*.{ts,tsx}
📄 CodeRabbit inference engine (.github/copilot-instructions.md)
components/**/*.{ts,tsx}: UI components should be placed in the components/** directory
Keep React components mostly presentational and lean, avoiding complex business logic
Files:
components/header/index.tsxcomponents/navigation-controls.tsx
**/*.{ts,tsx}
📄 CodeRabbit inference engine (.github/copilot-instructions.md)
Prefer TypeScript files over JavaScript
Run pnpm tsc --noEmit for TypeScript type-checking
Files:
components/header/index.tsxcomponents/navigation-controls.tsx
components/**/*.{ts,tsx,js,jsx}
📄 CodeRabbit inference engine (AGENTS.md)
Place UI and layout components in components/**
Files:
components/header/index.tsxcomponents/navigation-controls.tsx
**/*.{ts,tsx,js,jsx}
📄 CodeRabbit inference engine (AGENTS.md)
Prefer TypeScript for all code
Files:
components/header/index.tsxcomponents/navigation-controls.tsx
**/*.{js,jsx,ts,tsx}
📄 CodeRabbit inference engine (CLAUDE.md)
**/*.{js,jsx,ts,tsx}: Follow Prettier config with tabs, 4-space tabWidth, and 120-char printWidth
Prefer async/await over raw Promise chains in TypeScript/JavaScript code
Validate input with Zod where appropriate; follow existing schemas in lib/validations
Keep i18n-friendly: avoid hard-coded English strings in logic; use next-intl messages where relevant
Files:
components/header/index.tsxcomponents/navigation-controls.tsx
**/components/**/*.{jsx,tsx}
📄 CodeRabbit inference engine (CLAUDE.md)
**/components/**/*.{jsx,tsx}: For forms, prefer react-hook-form + Zod; follow patterns in existing auth/profile forms
Place business logic in lib/services or lib/repositories, not in components; keep components mostly presentational and data-fetching
Files:
components/header/index.tsxcomponents/navigation-controls.tsx
🧠 Learnings (2)
📚 Learning: 2025-11-30T21:22:22.296Z
Learnt from: CR
Repo: ever-works/ever-works-website-template PR: 0
File: CLAUDE.md:0-0
Timestamp: 2025-11-30T21:22:22.296Z
Learning: Applies to **/*.{js,jsx,ts,tsx} : Keep i18n-friendly: avoid hard-coded English strings in logic; use next-intl messages where relevant
Applied to files:
components/navigation-controls.tsx
📚 Learning: 2025-11-24T18:34:28.233Z
Learnt from: CR
Repo: ever-works/ever-works-website-template PR: 0
File: .github/copilot-instructions.md:0-0
Timestamp: 2025-11-24T18:34:28.233Z
Learning: Applies to components/**/*.{ts,tsx} : Keep React components mostly presentational and lean, avoiding complex business logic
Applied to files:
components/navigation-controls.tsx
🧬 Code graph analysis (2)
components/header/index.tsx (1)
lib/utils.ts (1)
isDemoMode(13-15)
components/navigation-controls.tsx (3)
hooks/use-header-settings.ts (1)
useHeaderSettings(9-22)lib/utils.ts (1)
isDemoMode(13-15)components/layout-switcher.tsx (1)
LayoutSwitcher(98-364)
⏰ Context from checks skipped due to timeout of 90000ms. You can increase the timeout in your CodeRabbit configuration to a maximum of 15 minutes (900000ms). (3)
- GitHub Check: cubic · AI code reviewer
- GitHub Check: Analyze (javascript-typescript)
- GitHub Check: Lint and Build
🔇 Additional comments (2)
components/header/index.tsx (1)
376-382: LGTM: Conditional rendering correctly gates LayoutSwitcher in mobile menu.The conditional logic properly restricts the LayoutSwitcher to demo mode while respecting the
layoutEnabledsetting. This aligns with the PR objective and maintains consistency with the desktop implementation inNavigationControls.components/navigation-controls.tsx (1)
13-23: LGTM: Conditional rendering correctly implements demo-mode gating.The refactored structure is clean and the conditional logic properly restricts the LayoutSwitcher to demo mode while respecting the
layoutEnabledsetting. The implementation is consistent with the changes incomponents/header/index.tsxand maintains appropriate responsive behavior.
The Layout combobox in the header is now only visible in DEMO mode. For deployed sites (non-DEMO), layout switching remains available only through Settings.
Summary
Related Issues
Description
Changes Made
Screenshots / Videos
Type of Change
Implementation Details
Testing Instructions
Deployment Notes
Checklist
Additional Context
Summary by cubic
Show the Layout switcher in the header only in DEMO mode to reduce clutter in production. Non-DEMO sites can still change layout from Settings.
Written for commit 356b03c. Summary will update on new commits.
Summary by CodeRabbit
✏️ Tip: You can customize this high-level summary in your review settings.