Console UI Revamp
Status
Implemented. Branch feature/console-ui-revamp.
Related Requirements
- Admin Console v1.0 look-and-feel; client §5 "no UI-only features" (every surface stays backed by the same APIs). Demo-freeze polish for the Anil walkthrough.
Problem Statement
The console was dark-only with an ad-hoc theme. The freeze needed a single sophisticated design language, a real light/dark toggle, a credible terminal, and seamless replay of the now-real SSH session recordings (OP-D089) — all without changing a single existing journey.
Architectural Intent
The UI is Tailwind + shadcn-style design tokens, so the entire console is
re-skinned by redefining the token set rather than editing components. This keeps
all component logic, labels, navigation, and data-testids intact (61 tests stayed
green) while changing only the design layer.
What Was Implemented
- Dual-theme token system (
globals.css): a light "paper + ink" default and a refined dark counterpart sharing one confident blue accent.:root= light,.dark= dark; surfaces are solid + hairline + soft-shadow in light, glass in dark. - Light/dark toggle (
theme-toggle.tsx) persisted tolocalStoragewith a no-flash init script inlayout.tsx(honors saved choice then system preference). - Display serif headings, Inter body, JetBrains Mono — applied via tokens and a
.font-displayutility on page titles. - macOS terminal chrome (traffic lights, dark window) on the live SSH terminal; the terminal stays dark in both themes (the one true terminal surface).
- Seamless session-recording replay (
ssh-recording-replay.tsx): for any session with a real recording (recordingSha256=sha256:…), an operator/auditor can replay the captured transcript in an xterm with a light streaming cadence. Fetched via the new proxy route/console-api/oneprotect/rmm/ssh-sessions/{id}/recording.
Components Involved
globals.css,tailwind.config.ts,layout.tsx,theme-toggle.tsx,app-shell.tsx,page-primitives.tsx,ssh-terminal.tsx,ssh-recording-replay.tsx,console-pages.tsx, console-api recording proxy route.
APIs / Events / Schemas
No backend change. Replay consumes the existing
GET /api/v1/rmm/ssh-sessions/{id}/recording (OP-D089) via the operator proxy.
Security / Tenant Isolation
Replay reuses the operator-auth proxy and the backend's tenant-scoped, role-gated recording read (operator-owner / auditor / admin). No new exposure.
Validation Steps
UI Validation
Toggle light/dark in the topbar (persists). Navigate every page — all journeys unchanged. On an asset with a completed SSH session, press Replay session to watch the recorded transcript play back in the terminal.
Smoke / Tests
frontend: typecheck + 62 tests green (incl. ssh-recording-replay.test.tsx
asserting the replay fetches the recording endpoint).
Known Limitations
- Replay streams output at a fixed cadence (no per-keystroke timing); asciicast-style timed replay is a follow-up.
- Recording is available only for completed sessions on the live backend (fixture mode shows a graceful "unavailable" state).
Follow-Up Work
- Timed asciicast replay; per-page density polish; optional theme = "system".
Round 2 — full-size terminal & replay modal
The live terminal and recording replay were cramped in the ~380px asset side
column. They now launch in a fixed, centered modal (components/ui/modal.tsx:
backdrop + Escape + click-outside + close button), max-w-5xl with a 60vh
terminal. The terminal connects when the modal opens and tears down on close
(open → effect → openTerminal; close → dispose socket + xterm), so it can be
opened, closed, and replayed any number of times cleanly. The inline panels are
now compact launchers. Functionality, journeys, and test-ids unchanged
(typecheck + 62 tests green).
Acceptance Criteria Mapping
Admin Console look-and-feel refreshed with light/dark + terminal + seamless recording replay, all existing functionality preserved (token-driven re-skin; green tests).