5.4 KiB
type, title, description, tags, timestamp
| type | title | description | tags | timestamp | ||||||
|---|---|---|---|---|---|---|---|---|---|---|
| guide | Authenticated Shell | How a signed-in user experiences the post-login shell, including authenticated event streaming. |
|
2026-07-22T09:03:53Z |
When this view is available
The authenticated shell is the post-login UI rendered by HomeComponent
(frontend/src/app/features/home/home.component.ts). It is gated by the client
authGuard and the JWT-protected /api/v1/events/status stream.
A user who is not signed in, or whose session has expired, is sent to /login
before the shell mounts.
How to access (tester steps)
- Ensure the instance is initialized. If not, follow First-Run Bootstrap.
- Sign in via
/loginas an admin or player. - Confirm the browser lands on
/challengesand renders the shell.
Expected behavior
Header
| Element | Selector | Expected |
|---|---|---|
| Page title | [data-testid="shell-title"] |
Shows the bootstrap pageTitle; clicking navigates to /challenges. |
| Active section | [data-testid="shell-active-section"] |
Shows Challenges, Scoreboard, Blog, or Admin based on the URL. |
| Event LED | [data-testid="shell-led"] |
A 10×10 circular dot whose color reflects the current event state. See Event LED colors below. |
| Countdown | [data-testid="shell-countdown"] |
Displays DD:HH:mm, Event ended, or empty for an unconfigured event. |
| User menu | [data-testid="user-menu-trigger"] |
Toggles rank, change-password, optional admin, and logout entries. |
Event LED colors
The LED is rendered by ShellHeaderComponent as a <span class="led">
with one of four state classes attached via [class.led-<state>]. The
visual styling lives in frontend/src/styles.css and is driven entirely
by the existing theme color tokens — there is no per-state color in
TypeScript.
| Event state | CSS class | Color token | Approx. hex | Visual |
|---|---|---|---|---|
countdown |
led led-countdown |
--color-warning |
#f59e0b |
Yellow filled dot |
running |
led led-running |
--color-success |
#10b981 |
Green filled dot |
stopped |
led led-stopped |
--color-danger |
#ef4444 |
Red filled dot |
unconfigured |
led led-unconfigured |
--color-secondary |
#64748b |
Neutral gray filled dot |
The base .led rule paints a 10×10 circular inline-block, so the LED
is always the same size and shape — only the background color changes
between states. The element also carries
aria-label="Event status: <state>" for assistive tech.
Quick tabs
The tab strip [data-testid="quick-tabs"] contains Challenges, Scoreboard, and
Blog. Clicking a tab navigates to its matching route; the active tab is marked
with the active class.
Live event window
HomeComponent.ngOnInit()startsEventStatusStorewithAuthenticatedEventSourceService.open('/api/v1/events/status').- The transport uses
fetch, sendsAccept: text/event-stream, includesAuthorization: Bearer <access-token>when available, and sends credentials. - It parses SSE
event:anddata:lines, buffers frames until a message listener is registered, and dispatchesMessageEventpayloads. - The store applies each state frame and advances countdown values with a local one-second tick between server pushes.
- Leaving the shell closes the source, aborts the fetch, and clears the tick.
A failed HTTP response, missing stream body, or streaming failure dispatches an error event. The shell retains the last event state until a later connection succeeds.
Architecture map
| File | Responsibility |
|---|---|
frontend/src/app/features/home/home.component.ts |
Hosts the shell and starts/stops the authenticated event stream. |
frontend/src/app/core/services/authenticated-event-source.service.ts |
Fetch-based authenticated SSE transport with abort and frame parsing. |
frontend/src/app/core/services/event-status.store.ts |
Applies event frames and derives the live countdown. |
frontend/src/app/features/shell/header/shell-header.component.ts |
Renders event LED, countdown, navigation, and user menu. |
frontend/src/styles.css |
Defines the .led base shape plus the four .led-{state} background-color rules keyed on theme tokens. |
frontend/src/app/features/shell/tabs/quick-tabs.component.ts |
Renders the main navigation tabs. |
tests/frontend/authenticated-event-source.spec.ts |
Verifies authorization headers, SSE frame delivery, and anonymous header omission. |
Tester flows
Live event window
- Configure a future start time and confirm the countdown LED and text appear.
- Move the start time into the past and the end time into the future; confirm the LED changes to running and the countdown counts toward the end.
- Move the end time into the past; confirm
Event endedand the stopped LED. - Remove either setting; confirm the unconfigured LED and empty countdown.
Navigation and logout
- Click each quick tab and confirm the matching route and active styling.
- Open the user menu and click Logout.
- Confirm navigation to
/loginand that the event stream is closed.