V1 Web PWA · Surface walkthrough

Veritas · claim mode

A per-surface walkthrough of the V1 Web PWA customer surface: layout, states, interactions, data, and cross-references.

walked
8sections4 minread

On this page

Context. surface customer · domain veritas · route /veritas/claim · auth signed-in · source apps/oshun/web/src/app/veritas/claim/page.tsx

Last walked. 2026-05-29 automated runtime walk (Playwright headless) — render, /v1 data (2xx), console/page-errors, expected content, screenshot verified; live screen-reader, touch, offline, and telemetry-delivery checks pending a manual AT pass. Evidence: WALKTHROUGH/results/runtime-sweep-2026-05-29.md; content re-verified 2026-06-03 against current source

Purpose#

The "read with the seams showing" view. Every sentence in the story is underlined by its confidence band (high / medium / low) and footnoted with a superscript that opens the matching evidence card in the rail. The thin server component awaits getVeritasClaim() and renders VeritasClaim.

Entry points#

  • Veritas sub-nav — verify which LSubNav item points here (the room declares lead | topics | sources | updates only; /veritas/claim is likely a deep link rather than a primary tab)
  • Linked from /veritas — verify whether the "Read sources" or article action surfaces this view
  • Linked from /veritas/story — story timeline → claim mode for an individual entry (verify)
  • Direct URL / bookmark — yes (auth required)

Layout regions#

page.tsx is a thin server component: await getVeritasClaim()<VeritasClaim>. VeritasClaim delegates the interactive board to the 'use client' VeritasClaimInteractive component, which mounts LWebShell with LCustomerNav active="library".

  • Header: Lilith customer nav (Library tab active)
  • Masthead (VrMast): top rule labelled Veritas · the broadsheet | reading · claim mode · on | N claims · M sources, then a large display title "Read with the seams showing." and an italic lede paragraph
  • Article column (left, 1.5fr):
    • Kicker eyebrow, headline (44px serif), byline eyebrow
    • Body paragraphs where each sentence is either plain text or a focusable claim button (underline colour + superscript footnote driven by sentence level and src)
    • Legend card: How to read the lines — three coloured underlines mapping high / medium / low to copy
  • Evidence column (right, 1fr):
    • VrHead: — · Evidence · open · What stands behind the lines. · hover, focus, or click
    • Selected claim card (Selected · sup. N · "..."): the active claim text, a confidence bar with percent fill, confidence · 0.NN / M sources align row, and a stack of source rows with VrBand chips, date eyebrow, and italic quote
    • VrHead: — · All N claims · Confidence at a glance.
    • Claims table: one row per claim with italic text, a coloured confidence bar, and a .NN mono number

States#

  • LoadinggetVeritasClaim() awaited server-side; suspends until resolved (no client skeleton)
  • Populated — fixture renders one selected claim plus the rest of the claim table
  • No selected claim — code path renders data.selected directly; the "no selection" branch is not present in this component
  • Error (recoverable)getVeritasClaim() rejects → falls through to the nearest error.tsx boundary
  • Offline — service worker serves cached HTML/JS; claim selection is client-local and needs no network fetch once the shell has loaded
  • Standalone PWA — verify the masthead and grid render at narrow breakpoints (page uses fixed 56px lateral padding)
  • Empty — N/A; the fixture always returns paragraphs and a table
  • Gated — none coded in this page

Interactions#

Body sentences (data-veritas-claim-inline)#

  • Underlined sentence (button) — hover, focus, and click update the right rail's data-veritas-selected-claim to the sentence src
  • Superscript footnote (<sup>) — rendered inside the button; the colour matches the sentence level and the parent button carries aria-controls="veritas-selected-claim" / aria-pressed

Legend card — "How to read the lines"#

  • Three coloured swatches — non-interactive; verify accessibility name (the swatch is a 24×0 div with border-bottom; needs SR text or aria-label)

Selected-claim card (right rail)#

  • Selected eyebrowSelected · sup. <sup> · "<text>"; updates as the user hovers/focuses/clicks a claim or table row
  • Confidence bar — visual element with data.selected.confidence percent width; verify SR text e.g. "confidence 0.NN, M sources align"
  • Source row (per source)
    • VrBand chip (A / B / C / D) — colour swatch + small italic descriptor ("A · primary or independent", etc.); verify SR-readable
    • Source name (italic serif) + date eyebrow + italic quote — each selected source row is an anchor with data-veritas-selected-source-row, data-veritas-source-name, data-veritas-source-band, and href="/veritas/source"

Claims table#

  • Each row — three-column button (text, bar, mono confidence); rows with sup update the selected-claim card on focus/click

Data & contracts#

  • Reads: getVeritasClaim() from @/lib/lilith-data/veritas-depth — returns VeritasClaimData ({ story, paragraphs[].sentences, selected, claimInspections, table })
  • Writes: none
  • Realtime: none
  • Caching: server fetch; revalidation per fixture policy
  • Auth/role check: shell middleware (verify)
  • Page metadata: title: "Veritas · claim mode", description "Read with the seams showing — every assertion underlined by its confidence and footnoted to the evidence.", alternates.canonical: /veritas/claim

Cross-references#

  • Component: apps/oshun/web/src/components/lilith/veritas.tsxVeritasClaim wrapper
  • Component: apps/oshun/web/src/components/lilith/VeritasClaimInteractive.tsx — claim-mode client board, selected rail, source links
  • Data: apps/oshun/web/src/lib/lilith-data/veritas-depth.ts (getVeritasClaim)
  • Sibling routes:
  • Component shared with: VrMast, VrHead, VrPip, VrBand (defined in veritas.tsx) and matching claim-mode atoms in VeritasClaimInteractive
  • Feature spec: V1/features.md

Open questions / known gaps#

  • The lede promises "hover any line; the rail opens what stands behind it"; VeritasClaimInteractive now wires hover/focus/click to the selected rail
  • Keyboard affordance for cycling between claims: underlined claims and claims-table rows are buttons
  • LCustomerNav active="library" puts this view under Library — consistent with the /veritas hub, which also uses active="library" (the earlier "hub uses Explore" premise is false; no inconsistency)
  • Confirm whether the page sets dynamic or uses ISR/static rendering