added public sites side bar

This commit is contained in:
Oliver Kieselbach
2026-03-18 12:04:27 +01:00
parent c79459ee0a
commit d8445a60b0
7 changed files with 39 additions and 23 deletions
@@ -1,13 +1,11 @@
import Link from "next/link";
import { PublicPageHeader } from "../../components/PublicPageHeader";
import { PublicSiteNavbar } from "../../components/PublicSiteNavbar";
const VERSION = "1.0.0";
export default function AboutPage() {
return (
<div className="min-h-screen bg-gray-50">
<PublicSiteNavbar showSectionLinks={false} />
<PublicPageHeader title="About" />
<main className="px-4 sm:px-6 lg:px-8 py-8 space-y-6">
<div className="bg-white rounded-lg shadow p-6">
@@ -1,13 +1,10 @@
"use client";
import Link from "next/link";
import { PublicPageHeader } from "../../components/PublicPageHeader";
import { PublicSiteNavbar } from "../../components/PublicSiteNavbar";
export default function ChangelogPage() {
return (
<div className="min-h-screen bg-gray-50">
<PublicSiteNavbar showSectionLinks={false} />
<PublicPageHeader title="Changelog" />
<main className="px-4 sm:px-6 lg:px-8 py-8">
<div className="bg-white rounded-2xl shadow-sm border border-gray-200 p-8 sm:p-10">
@@ -1,11 +1,8 @@
import Link from "next/link";
import { PublicPageHeader } from "../../components/PublicPageHeader";
import { PublicSiteNavbar } from "../../components/PublicSiteNavbar";
export default function PrivacyPage() {
return (
<div className="min-h-screen bg-gray-50">
<PublicSiteNavbar showSectionLinks={false} />
<PublicPageHeader title="Privacy Policy" />
<main className="px-4 sm:px-6 lg:px-8 py-8 space-y-6">
<div className="bg-white rounded-lg shadow p-6">
@@ -1,11 +1,8 @@
import Link from "next/link";
import { PublicPageHeader } from "../../components/PublicPageHeader";
import { PublicSiteNavbar } from "../../components/PublicSiteNavbar";
export default function RoadmapPage() {
return (
<div className="min-h-screen bg-gray-50">
<PublicSiteNavbar showSectionLinks={false} />
<PublicPageHeader title="Roadmap" />
<main className="px-4 sm:px-6 lg:px-8 py-8">
<div className="bg-white rounded-2xl shadow-sm border border-gray-200 p-8 sm:p-10">
@@ -1,11 +1,8 @@
import Link from "next/link";
import { PublicPageHeader } from "../../components/PublicPageHeader";
import { PublicSiteNavbar } from "../../components/PublicSiteNavbar";
export default function TermsPage() {
return (
<div className="min-h-screen bg-gray-50">
<PublicSiteNavbar showSectionLinks={false} />
<PublicPageHeader title="Terms of Use" />
<main className="px-4 sm:px-6 lg:px-8 py-8 space-y-6">
<div className="bg-white rounded-lg shadow p-6">
@@ -6,8 +6,9 @@ import { usePathname } from "next/navigation";
import { useAuth } from "../contexts/AuthContext";
import { useSidebar, PageSectionItem } from "../contexts/SidebarContext";
import { CollapseState } from "../hooks/useSidebarState";
import { DefaultSectionIcon } from "../lib/sidebarIcons";
import { DefaultSectionIcon, BookOpenIcon, RocketLaunchIcon, InformationCircleIcon, DocumentTextIcon, ShieldCheckIcon } from "../lib/sidebarIcons";
import { DASHBOARD_ITEM, NAV_GROUPS, REGULAR_USER_ITEMS, NavItem, NavGroup } from "../lib/globalNavConfig";
import { PublicSiteNavbar } from "./PublicSiteNavbar";
// Sidebar pixel widths
export const SIDEBAR_PX: Record<CollapseState, number> = {
@@ -134,18 +135,23 @@ export function GlobalSidebar({ children }: { children: ReactNode }) {
// Docs pages are always accessible (public + authenticated)
const isDocsPage = pathname.startsWith("/docs");
// All public pages that should show sidebar + navbar
const PUBLIC_PATHS = ["/docs", "/terms", "/privacy", "/roadmap", "/about", "/changelog"];
const isPublicPage = PUBLIC_PATHS.some((p) => pathname === p || pathname.startsWith(p + "/"));
// Landing page: never show sidebar
if (pathname === "/") {
return <>{children}</>;
}
// Not authenticated and not docs: no sidebar
if (!isAuthenticated && !isDocsPage) {
// Not authenticated and not a public page: no sidebar
if (!isAuthenticated && !isPublicPage) {
return <>{children}</>;
}
// Whether the main Navbar is present (determines sidebar top offset)
const hasNavbar = isAuthenticated;
// Whether a top navbar is present (determines sidebar top offset)
// Authenticated users always have the app navbar; public pages have the PublicSiteNavbar
const hasNavbar = isAuthenticated || isPublicPage;
// --- Render helpers ---
@@ -156,6 +162,7 @@ export function GlobalSidebar({ children }: { children: ReactNode }) {
const isNavActive = (href: string) => {
if (href === "/dashboard") return pathname === "/dashboard" || pathname === "/";
if (href === "/") return pathname === "/";
return pathname.startsWith(href);
};
@@ -308,15 +315,35 @@ export function GlobalSidebar({ children }: { children: ReactNode }) {
</>
)}
{/* Public (unauthenticated): show Home link to landing page */}
{/* Public (unauthenticated): show public nav items */}
{!isAuthenticated && (
renderGlobalItem({ id: "home", label: "Home", href: "/", icon: DASHBOARD_ITEM.icon })
<>
{renderGlobalItem({ id: "home", label: "Home", href: "/", icon: DASHBOARD_ITEM.icon })}
<div className={`${collapseState === "full" || isMobile ? "mt-3" : "mt-1"}`}>
<ul className="space-y-0.5">
{renderGlobalItem({ id: "docs", label: "Docs", href: "/docs", icon: <BookOpenIcon /> })}
{renderGlobalItem({ id: "roadmap", label: "Roadmap", href: "/roadmap", icon: <RocketLaunchIcon /> })}
{renderGlobalItem({ id: "about", label: "About", href: "/about", icon: <InformationCircleIcon /> })}
{renderGlobalItem({ id: "terms", label: "Terms", href: "/terms", icon: <DocumentTextIcon /> })}
{renderGlobalItem({ id: "privacy", label: "Privacy", href: "/privacy", icon: <ShieldCheckIcon /> })}
</ul>
</div>
</>
)}
{/* Divider (only when both global nav and page sections exist) + page sections */}
{hasPageSections && (
<>
{/* Divider only when global nav is also shown */}
{/* Divider / spacing between nav and page sections */}
{!isAuthenticated && (
collapseState === "icons" && !isMobile ? (
<hr className="mx-2 my-2 border-blue-200 dark:border-blue-800" />
) : (
<div className="mt-4 mb-2 mx-3">
<hr className="border-gray-200 dark:border-gray-700" />
</div>
)
)}
{isAuthenticated && (
collapseState === "icons" && !isMobile ? (
<hr className="mx-2 my-2 border-blue-200 dark:border-blue-800" />
@@ -341,6 +368,9 @@ export function GlobalSidebar({ children }: { children: ReactNode }) {
return (
<>
{/* ===== Public pages: show branded navbar without section links ===== */}
{!isAuthenticated && isPublicPage && <PublicSiteNavbar showSectionLinks={false} />}
{/* ===== Mobile: overlay ===== */}
{mobileDrawerOpen && (
<div
File diff suppressed because one or more lines are too long