mirror of
https://github.com/block/buzz.git
synced 2026-10-30 14:01:37 +00:00
The deep-link dispatcher awaits InviteJoinNotifier.prepare before it presents the invite sheet, and prepare awaited GET /api/join-policy. On a slow or blackholed relay, opening an invite did nothing visible until discovery finished or hit the 30 s request deadline. prepare now returns once the pending invite and host are established and loads the policy in the background. A new isLoadingJoinPolicy state renders a "Loading community policy…" row (the spinner owns the announcement) and keeps Join disabled until the policy is shown or confirmed absent. A per-load token fences the result: a re-prepare, reset, or claim supersedes the load, so a stale success or failure cannot overwrite a claim that confirmJoin started, e.g. from the iOS native sheet. confirmJoin still re-reads the policy before it claims. The dispatcher gains a table with a suspended /api/join-policy response. Both rows assert that the host, an enabled Cancel, the loading row, and a disabled Join are visible before the GET resolves, with no claim. The policy row then claims once with the app-minted receipt after age confirmation and acceptance. The absent row claims once without a receipt after Join. The provider claim journey now claims while discovery is still suspended, then fails that discovery and asserts the join stays successful. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com> Signed-off-by: Matt Toohey <contact@matttoohey.com>