oficina / docs Public

Spec: close the cross-device seam, and bound the compaction horizon

The link-share-to-comment seam is resolved, jointly with the home
session, and it keeps capability entirely instance-side: the instance
builds a return URL carrying a nonce that keys its own pending state,
and redeems it after verifying the assertion. The home learns nothing
about links or capabilities, so identity-never-authorization survives
without a carve-out.

The cross-device half falls out of the same fix rather than needing its
own -- the nonce rides the URL rather than a cookie, so the round trip
reassembles in whichever browser opened the email. That is a good sign
the two were one problem.

Also states two things about compaction that a reader would otherwise
worry about or get wrong. Compaction does not strand an offline client,
because a snapshot encodes full state and the client just receives one
large update; what it costs is history between snapshots, not
reachability. And the horizon is a fixed period, never 'once every
client has caught up' -- that rule is unbounded in a hibernating fleet,
because a dormant consumer never advances while the table reads as
bounded. It has appeared twice in the home spec already.
Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_011F5CivVm4CmL9ByfSSAaXA
Paul Campbell pushed by paul@keymail.dev f5a1202dd2638e74b4d87b23a999a5dc11d7678d parent 3042ba5
1 file changed, +39 −8
  • docs/superpowers/specs/2026-08-30-docs-design.md +39 −8

No CI script — run details

diff --git a/docs/superpowers/specs/2026-08-30-docs-design.md b/docs/superpowers/specs/2026-08-30-docs-design.md
index 17d467f..2da9a67 100644
--- a/docs/superpowers/specs/2026-08-30-docs-design.md
+++ b/docs/superpowers/specs/2026-08-30-docs-design.md
@@ -167,6 +167,19 @@ Three mechanisms, all required:
- **A compaction horizon.** Beyond it, updates are collapsed into the
preceding snapshot and dropped.
+**Compaction does not strand an offline client, and this is worth stating
+because the naive reading says it does.** A snapshot encodes full state, so a
+client returning after the horizon receives one large update instead of many
+small ones and still converges — that is the CRDT's whole point. What
+compaction costs is *history* between snapshots, not reachability.
+
+**The horizon is a fixed period, never "once every client has caught up".**
+Any prune-when-all-consumers-have-advanced rule is unbounded in a
+hibernating fleet, because a dormant consumer never advances and the table
+grows forever while reading as bounded. That pattern has now appeared twice
+in the home spec — a `jti` store and a rekey journal — and this is the third
+place it would have fitted.
+
**Cutting the version timeline (§14) is what makes compaction tractable.**
With a browsable timeline, every historical point must remain reachable and
the log can never be collapsed. With named versions only, the set of points
@@ -413,14 +426,32 @@ single-use replay store churns against a guest population far larger than
the membership list and unbounded in time, so **it must be self-pruning,
sized by assertion lifetime rather than user count.**
-**Open seam: the cross-device magic link.** A link-share viewer who signs in
-to comment completes the link in whichever browser opens the email. The
-capability context must survive that round trip, or opening it on a phone
-strands the pending context on the laptop. `auth.Config.Authorize` is
-`func(address string) bool` and cannot carry document scope. The capability
-therefore rides the return-to through the home and the assertion returns to
-the originating origin. Designed here, but it is the seam where §8.2's
-central rule executes and it deserves a test of its own.
+**The cross-device magic link — closed 2026-08-30.** A link-share viewer who
+signs in to comment completes the link in whichever browser opens the email,
+so the capability context must survive that round trip or opening it on a
+phone strands the pending state on the laptop. `auth.Config.Authorize` is
+`func(address string) bool` and cannot carry document scope.
+
+The resolution keeps capability **entirely instance-side**, which is what
+makes it compatible with "assertions carry identity, never authorization":
+
+1. The instance builds the sign-in return URL with a **nonce**, keying
+ pending state it holds itself — the link token and what it grants.
+2. The person signs in at the home. The home learns nothing about links or
+ capabilities; it mints an ordinary assertion.
+3. On return the instance verifies the assertion, redeems its own pending
+ state by nonce, mints the grant, and only then applies the session.
+
+Because the nonce rides the URL rather than a cookie, the round trip
+reassembles in whichever browser opened the email — the cross-device problem
+falls out of the same fix rather than needing its own. *(Resolved jointly
+with the home session; the tempting alternative was letting the assertion
+carry the capability, which would have holed §5.3 of the home spec in the
+same week it was tightened.)*
+
+This is the seam where §8.2's central rule executes, and it gets its own
+test: an assertion for a person with no grant is a valid assertion that gets
+nothing, and the nonce redemption is what turns it into access.
### 8.2 Sharing