Refactor navigation item handling in App component to conditionally include admin link based on user role, improving access control and code clarity.
This commit is contained in:
@@ -46,13 +46,12 @@ const routeTree = rootRoute.addChildren([loginRoute, protectedRoute.addChildren(
|
||||
const router = createRouter({ routeTree, context: { session: null } })
|
||||
declare module '@tanstack/react-router' { interface Register { router: typeof router } }
|
||||
|
||||
const navItems = [
|
||||
const mainNavItems = [
|
||||
{ to: '/events', label: 'Events', icon: CalendarDays },
|
||||
...(demoMode ? [
|
||||
{ to: '/series/$seriesId' as const, params: { seriesId: 'series-1' }, label: 'Live', icon: Radio },
|
||||
{ to: '/bracket/$eventId' as const, params: { eventId: 'bracket-1' }, label: 'Bracket', icon: Trophy },
|
||||
] : []),
|
||||
{ to: '/admin', label: 'Admin', icon: Shield },
|
||||
]
|
||||
|
||||
function Brand() {
|
||||
@@ -70,6 +69,9 @@ function AppShell() {
|
||||
},
|
||||
})
|
||||
const initials = session.data?.account.displayName.slice(0, 2).toUpperCase() ?? 'MM'
|
||||
const navItems = session.data?.account.role === 'admin'
|
||||
? [...mainNavItems, { to: '/admin' as const, label: 'Admin', icon: Shield }]
|
||||
: mainNavItems
|
||||
return <div className="app-shell">
|
||||
<header className="topbar">
|
||||
<Brand />
|
||||
@@ -189,7 +191,7 @@ function AdminPage() {
|
||||
useEffect(() => { if (!selectedId && events.data?.[0]) setSelectedId(events.data[0].id) }, [events.data, selectedId])
|
||||
if (events.isLoading) return <LoadingState label="Loading admin control room…" />
|
||||
if (events.isError) return <ErrorState retry={() => void events.refetch()} />
|
||||
return <div className="page"><PageHeader eyebrow="Admin control room" title={createMode ? 'Create event' : selected?.title ?? 'No events yet'} description={selected ? `Registration closes ${new Date(selected.registrationDeadline).toLocaleString()}.` : 'Create the first community event.'} actions={<><select aria-label="Selected event" value={selected?.id ?? ''} onChange={(e) => { setSelectedId(e.target.value); setCreateMode(false) }}>{events.data?.map((event) => <option value={event.id} key={event.id}>{event.title}</option>)}</select><button className="button secondary" onClick={() => { setCreateMode(true); setTab('events') }}><Sparkles />New event</button></>} /><div className="tabs" role="tablist">{(['events', 'participants', 'balance'] as AdminTab[]).map((item) => <button key={item} role="tab" aria-selected={tab === item} className={tab === item ? 'active' : ''} disabled={!selected && item !== 'events'} onClick={() => setTab(item)}>{item === 'events' ? 'Event setup' : item === 'participants' ? 'Participants' : 'Balance teams'}</button>)}</div>{tab === 'events' && <EventSetup event={createMode ? undefined : selected} onCreated={(event) => { setCreateMode(false); setSelectedId(event.id) }} />}{tab === 'participants' && selected && <Participants eventId={selected.id} />}{tab === 'balance' && selected && <BalanceView eventId={selected.id} />}</div>
|
||||
return <div className="page"><PageHeader eyebrow="Admin control room" title={createMode ? 'Create event' : selected?.title ?? 'No events yet'} description={selected ? `Registration closes ${new Date(selected.registrationDeadline).toLocaleString()}.` : 'Create the first community event.'} actions={<>{events.data && events.data.length > 0 && <select aria-label="Selected event" value={selected?.id ?? ''} onChange={(e) => { setSelectedId(e.target.value); setCreateMode(false) }}>{events.data.map((event) => <option value={event.id} key={event.id}>{event.title}</option>)}</select>}<button className="button secondary" onClick={() => { setCreateMode(true); setTab('events') }}><Sparkles />New event</button></>} /><div className="tabs" role="tablist">{(['events', 'participants', 'balance'] as AdminTab[]).map((item) => <button key={item} role="tab" aria-selected={tab === item} className={tab === item ? 'active' : ''} disabled={!selected && item !== 'events'} onClick={() => setTab(item)}>{item === 'events' ? 'Event setup' : item === 'participants' ? 'Participants' : 'Balance teams'}</button>)}</div>{tab === 'events' && <EventSetup event={createMode ? undefined : selected} onCreated={(event) => { setCreateMode(false); setSelectedId(event.id) }} />}{tab === 'participants' && selected && <Participants eventId={selected.id} />}{tab === 'balance' && selected && <BalanceView eventId={selected.id} />}</div>
|
||||
}
|
||||
|
||||
function toLocalInput(value: string) {
|
||||
|
||||
Reference in New Issue
Block a user