Offline & queued actions
What this framework ships for flaky-network ERP reality — and, stated just as plainly, what it deliberately does not. The split is the same one every page here follows: the framework does visuals and contracts; the queue engine, storage and replay are your app's (the reference products sell session persistence as a server; a CSS framework pretending to ship it would be selling air). Not a promise of offline-first — if your deployment needs true offline capture, that is an application architecture (service worker, local store, idempotent replay) this page gives you the visible half of, nothing more.
The four states a user must be able to tell apart
| State | Chip | Announced | Meaning for the user |
|---|---|---|---|
| Online | Online | "Connection: online" | acting saves now |
| Syncing | Syncing | "Connection: syncing changes" | recent work is in flight; leaving now may lose the tail |
| Queued | 3 queued | "Connection: offline, 3 actions queued" | work is captured, not saved — the COUNT is the honesty: "offline" alone hides how much is at risk |
| Error | Sync error | "Connection: sync failed, retry needed" | replay hit something a retry alone will not fix — this state must never decay back to a quiet glyph |
Every state is two-channel by
shape: the glyph differs in FORM (● ↻ ⏸ ✕), never only in
colour, and the text says the state in words. Changes are announced
through one aria-live="polite" region beside the chip —
polite, because a connection blip mid-sentence is context, not an
emergency. Zero new CSS: this is
badge composition, and the
slot's fixed home is the
app frame's top bar — a
status that moves between screens is a status users stop finding.
The contract your queue engine owes the chip
| Rule | Why |
|---|---|
| Both channels move in one place, together | a chip that says Online while the live region still says queued is worse than either alone |
| The queued state carries the count | "3 queued" is a fact the user can weigh before walking out of wifi range; "offline" is a mood |
| Queued actions must be idempotent on replay | a reconnect that re-posts a claim or a scan twice turns signalling into data corruption; design the server so replay is safe (the same 409 discipline every pattern here documents) |
| Error is sticky until acted on | auto-clearing a failed sync teaches users the red state means nothing |
| Screens stay honest about what is local | a row that exists only in the queue renders with a queued cue (a badge), not disguised as saved — the RF pages' session-lost rows follow the same rule |