"use client";
import { usePathname, Link } from "@/i18n/routing";
import {
ShellAppShell,
ShellCollapsibleNav,
ShellNavItem,
useShellNav,
} from "@reopt-ai/opt-shell";
import { useOptTheme } from "@reopt-ai/opt-ui";
import {
Activity,
BookOpen,
ChevronRight,
Database,
GitBranch,
Layers3,
Menu,
Moon,
Sun,
} from "lucide-react";
import type { ShellExampleApp } from "@/data/example-apps";
import { CONSOLE_ROOT } from "./data-console-shared";
import s from "./data-console.module.css";
export function DataConsoleFrame({
children,
}: {
app: ShellExampleApp;
children: React.ReactNode;
}) {
const pathname = usePathname();
const { resolvedMode, setMode } = useOptTheme();
const current = pathname.includes("/pipelines/")
? "Pipeline detail"
: pathname.endsWith("/pipelines")
? "Pipelines"
: pathname.endsWith("/welcome")
? "Workspace guide"
: "Overview";
return (
<ShellAppShell
className={s.app}
contentClassName={s.main}
header={
<div className={s.topbar}>
<Link href={CONSOLE_ROOT} className={s.brand}>
<span className={s.brandMark}>
<Layers3 size={17} />
</span>
Data Console
</Link>
<span className={s.topSeparator} />
<span className={s.topWorkspace}>Acme / Data platform</span>
<ChevronRight size={12} />
<span className={s.current}>{current}</span>
<div className={s.topRight}>
<span className={s.environment}>
<i />
Production
</span>
<span className={s.region}>aws · us-east-1</span>
<button
type="button"
className={s.iconButton}
aria-label={
resolvedMode === "dark"
? "Switch to light theme"
: "Switch to dark theme"
}
onClick={() =>
setMode(resolvedMode === "dark" ? "light" : "dark")
}
>
{resolvedMode === "dark" ? <Sun size={15} /> : <Moon size={15} />}
</button>
<span className={s.avatar} title="Alex Kim · Data platform">
AK
</span>
</div>
</div>
}
mobileHeader={<MobileHeader />}
nav={
<ShellCollapsibleNav
width={196}
collapsible={false}
showToggle={false}
className={s.nav}
label="Data Console navigation"
>
<div className={s.navInner}>
<div className={s.workspace}>
<span className={s.workspaceIcon}>
<Database size={16} />
</span>
<div>
<strong>Data platform</strong>
<small>Acme workspace</small>
</div>
</div>
<nav className={s.navLinks} aria-label="Workspace pages">
<ShellNavItem
href={CONSOLE_ROOT}
active={pathname === CONSOLE_ROOT}
icon={<Activity size={16} />}
>
Overview
</ShellNavItem>
<ShellNavItem
href={`${CONSOLE_ROOT}/pipelines`}
active={pathname.includes("/pipelines")}
icon={<GitBranch size={16} />}
>
Pipelines <span className={s.navCount}>6</span>
</ShellNavItem>
<ShellNavItem
href={`${CONSOLE_ROOT}/welcome`}
active={pathname.endsWith("/welcome")}
icon={<BookOpen size={16} />}
>
Workspace guide
</ShellNavItem>
</nav>
<div className={s.navSaved}>
<span>Needs attention</span>
<Link href={`${CONSOLE_ROOT}/pipelines/payment-sync`}>
<i className={s.dangerDot} />
payment-sync
</Link>
<Link href={`${CONSOLE_ROOT}/pipelines/log-agg`}>
<i className={s.warningDot} />
log-aggregator
</Link>
</div>
<div className={s.navBottom}>
<span className={s.environment}>
<i />
Scheduler online
</span>
<small>Sample data · read-only sources</small>
<div>
<span className={s.avatar}>AK</span>
<span>
<strong>Alex Kim</strong>
<small>Platform engineer</small>
</span>
</div>
</div>
</div>
</ShellCollapsibleNav>
}
>
{children}
</ShellAppShell>
);
}
function MobileHeader() {
const { open } = useShellNav();
return (
<div className={s.mobileBar}>
<button
type="button"
className={s.iconButton}
aria-label="Open menu"
onClick={open}
>
<Menu size={18} />
</button>
<span>Data platform</span>
<span className={s.muted}>Sample workspace</span>
</div>
);
}