#279 · Wave 1PRD-0005 R8ADR-0018 · ratifiedbuilt against #532 · GET / on-device
The three presentation states for a Sprout that lives on the windowsill, drawn against the real served status — not an imagined payload. Hardens the connection-states sketch from the Untethered exploration (PR #249); the state lives in a chip + one line, never in the numbers.
What the device actually saysGET / · text/plain · read-only, nothing actuates (#532)
$ curl http://sprout.local/
{{ payloadText }}
curl: (7) Failed to connect to sprout.local — no route to host
LAST-KNOWN SNAPSHOT · viewer-stamped {{ lastHeardLabel }} — the viewer's clock, never the device's claim
{{ payloadText }}
the mapping ruleEvery pixel of the glance traces to a served field — wifi= + fetch result → the chip; chN level/raw/quality → the rows; fw/git/board/ip/uptime_ms → the footer. What isn't served isn't shown as fact: sync progress is the store's claim (hub-side), and "last heard" is the viewer's clock. The device never claims wall-time — time: uptime until NTP/RTC lands (#21).
The three stateschip + one voice line + one rule each — numbers stay clean
beneath them: the device's own wifi state (served verbatim as wifi=…)
wifi={{ w.name }} · {{ w.note }}
The chip is the viewer's state; wifi= is the device's — you mostly read connecting/failed over serial or after the fact, since an unreachable device can't serve you its own bad news.
Per-channel quality — the served enum, verbatimquality gates the band: an untrusted reading never wears a band color
{{ q.flag }}{{ q.when }}{{ q.treatment }}
States & seams — build noteswhat changed vs the exploration, and where each fact comes from
{{ nt.tag }}{{ nt.text }}
#279 · one contract, both modes — only transport and presentation differ (ADR-0018)tend well.