Context & Investigations
Operating Status
The header status ring generalises from "offline?" to "anything need attention?" — tap it for health-at-a-glance rows plus a needs-attention list.
Situation
Wave 1-C, the last piece of Wave 1. The header status ring only ever reflected session.offline, filling oxblood when a line was held and otherwise sitting as a non-interactive dot. There was no way to see whether the wider system was healthy — a provider down, D1 unreachable, the Hub gone stale, a dig failed — even though that information already existed (/status, investigation statuses, signal timestamps).
Decided in brainstorming: tapping the ring opens an operating-status sheet showing four health rows plus a "needs attention" list of live errors, built entirely from data already available — no runtime changes, no migrations.
Key decisions
Ring generalises
Fills oxblood whenever anything needs attention — offline, a failed dig, a provider/DB down, or a stale Hub — not just offline.
Reuse only, no new plumbing
Extends the existing GET /status with a hub block and reuses already-loaded investigations plus client offline state; no runtime or migration changes.
Pure derivation core
deriveOperatingStatus() takes {status, investigations, offline, now} and returns rows + attention + needsAttention — the testable heart of the feature.
Never falsely all-well
A null/failed /status fetch renders every dependent row as "Unknown" (warn) rather than silently showing everything fine.
On-demand refresh only
/status loads once on mount and re-fetches on each ring tap — no continuous polling.
Signal freshness, not signal prose
The Hub row uses signal *freshness*, not the free-form status signal's body text — a possible future iteration, explicitly out of scope now.
Architecture
One small server-side helper feeds an extended health endpoint; a pure web helper turns that plus client state into rows and attention items for a new sheet.
signalsHealth(env) — newest signal timestamp across KNOWN_SIGNALS plus a freshness boolean.GET /status extended with hub: await signalsHealth(env); db/providers unchanged.deriveOperatingStatus() — pure function producing Connection/Brain/Memory/Hub rows plus the attention list..sheet/.overlay), rows plus attention list with per-item "Retry →" for failed digs.<button>; loads /status on mount and on tap; renders the sheet.Risks & guardrails
Ring lag on Hub staleness
A Hub going stale mid-session won't redden the ring until the next tap — accepted, since offline/failed-dig conditions redden it instantly regardless.
Provider-tier mapping
"Capable provider available" maps to on-form/fallback via tier; kept simple, exact copy tuned in the plan.
Deterministic relative time
now is injected into the pure helper so "8m ago" staleness math is testable.
Delivery
Hub freshness
signalsHealth() derived from the signal store.
Status endpoint
Add hub to GET /status.
Web types + loader
StatusResponse type + loadStatus().
Derivation helper
deriveOperatingStatus() — the pure, fully-tested core.
Sheet component
StatusSheet.svelte.
Ring wiring
Ring → button → sheet in +page.svelte.
Out of scope
docs/superpowers/specs/2026-06-12-operating-status-design.mdplan ·
docs/superpowers/plans/2026-06-12-operating-status.md