Thirteen routes, a consistent component kit, and real evidence behind every screen. What it lacks is a hierarchy that answers what needs attention now, and one visual system rather than three overlapping ones. Fourteen findings, ordered by what they cost the reader.
14findings
8blocking
15screens rebuilt
2themes
Findings
01NavigationBlocking
Thirteen destinations, no groups, four of them governance
The rail lists Overview through Settings as equal peers. Governance, Authorization, Shadow Agents and Quarantine are one subject split four ways, and nothing in the rail says which one holds the thing you came for.
Fix
Group the rail into Monitor, Govern, Evidence, Admin. Keep the four governance routes, but under one heading, with open counts on the rail so a reviewer can see where the work is.
02NavigationBlocking
A bearer token field lives in the primary navigation
The sidebar ends with an API token input whose placeholder is a sentence of instructions, present on every screen, for every role. It reads as a dev affordance that shipped.
Fix
Move it to Settings behind an admin check, and show identity in the rail instead: who you are signed in as, your role, and licence expiry.
03Visual systemBlocking
Eleven type sizes, most of them half-pixel
10.5, 11.5, 12, 12.5, 13, 13.5, 15.5, 21, 26 — plus one-off padding like 15px 17px. The sizes are close enough that nothing reads as a level, so every card looks the same weight as every other card.
Fix
Six steps: 11 mono caps for labels, 13 body, 13.5 table, 17 section, 30 page, mono numerals for figures. Serif only for page and section titles, so hierarchy comes from face and size rather than from weight alone.
04Visual systemWorth fixing
The dark theme is a commented-out block
index.css defines every token, then leaves .dark as a comment noting it lands in a later phase. A compliance console gets read in windowless rooms and on projectors.
Fix
Ship both themes off the same tokens now — the redesign's palette is one variable block per theme, no component changes.
05HierarchyBlocking
Overview gives its headline number a quarter of the width
The portfolio gauge, the four-quarter trend, days-to-report and agent count occupy identical tiles. The failing-agent list — the only part anyone can act on — renders below them, and only when non-empty, so the page silently changes shape.
Fix
Lead with the score against its ControlBook floor, then a Needs a decision list that is always present and says so when it is empty.
06HierarchyWorth fixing
Cards inside cards inside a scrolling page
The agents table is a 560px scroll area inside a card inside a page that also scrolls, and both the drift timeline and the certify panel expand below it, pushing content down and able to be open at once.
Fix
One scroll per screen. Put agent detail in a persistent side panel next to the table with tabs for drift, certification and evidence.
07Data densityWorth fixing
Six badge variants across two unrelated meanings
Risk tier and lifecycle state use the same pill shape and the same palette, so HIGH and CERTIFIED are visually interchangeable. Severity, pass/fail and a purple accent all share it too.
Fix
Reserve tinted pills for risk and severity. Set lifecycle as plain text and drift as a coloured dot with a word, so a row has one loud element, not four.
08Data densityWorth fixing
Identifiers and numbers are typographically ordinary
Agent IDs use mono in some cells and not others; scores are tabular but sit at body size next to labels of the same weight.
Fix
Mono for every identifier, hash and figure, at one size, right-aligned in numeric columns. It makes a column of scores scannable without any colour at all.
09CopyBlocking
The console speaks in internal vocabulary
GoldScore, drift, gate, ASI coverage, anchoring run and the empty state No agents registered (memory mode) all assume the reader built the product. An external auditor is a named persona for this console.
Fix
Give each first use a one-line gloss in the section subhead. Replace mode language with what the reader can do next.
10StatesBlocking
Loading is a sentence, empty is an apology
Every page renders Loading overview… as plain muted text, then swaps in a full layout. Errors are red body text with a Retry button and no diagnosis. Empty states offer nothing to do.
Fix
Skeleton rows that match the real layout, errors that name what failed and whether evidence is affected, and empty states with the one action that resolves them.
11CertificationBlocking
The signed record is presented as a form footer
Certification is the product's central act — an interactive human identity, a signed and hash-chained record — and its result renders as a bordered div below the inputs, with the cert ID in the same grey as the helper text.
Fix
Treat it as a receipt: certifier, version, cert ID, expiry, conditions and the exact offline verify command, laid out as a record rather than as feedback.
12CertificationWorth fixing
Segregation of duties surfaces as a paragraph
The panel warns in prose that the same person cannot certify twice in a row; the button stays enabled until the server refuses.
Fix
Evaluate it up front: disable the action, say why on the button, and name who can sign instead.
13GovernanceBlocking
One route carries six panels and 1,100 lines
Obligation coverage, authority model, escalations, recertifications, integrity and framework mappings stack vertically with no in-page navigation, and the period control at the top governs only some of them.
Fix
A sticky section rail with counts, sections that each own their period scope, and the two time-critical panels — escalations and recertifications — above the reference material.
14ResponsiveMinor
Fixed rail, fixed padding, horizontal scroll
A 224px rail and 28px page padding never change, and wide tables resolve to overflow-x, which hides the action column first.
Fix
Collapse the rail to labels-off below 1100px, keep the action column pinned, and let secondary columns drop before the ones a decision depends on.
Every finding above is designed, not only described: the accompanying HTML carries fifteen rebuilt screens in both themes, each with its ready, loading, empty and error states, plus the token block and navigation grouping as apply-ready code.