Repository navigation
Open
Labels
app/idPackage/app: id (pkgs/ or apps/ in this repo)Package/app: id (pkgs/ or apps/ in this repo)effort/mMedium: expected under 1 day of workMedium: expected under 1 day of workkind/infrastructureInfrastructure / host-portability workInfrastructure / host-portability workmeta/enrichedIntake review done: acceptance criteria, links, and normalized labels addedIntake review done: acceptance criteria, links, and normalized labels addedmode/onlineFully doable remotely: design, config, code, cloudFully doable remotely: design, config, code, cloudpriority/normalOrdinary priority (the default)Ordinary priority (the default)queue/blockedQueue or user escalation stateQueue or user escalation statequeue/queuedHas a queued task in the Supabase agent queueHas a queued task in the Supabase agent queuesource/humanFiled directly by a humanFiled directly by a humanstatus/blockedQueue or user escalation stateQueue or user escalation stateuser/escalatedQueue or user escalation stateQueue or user escalation state
Description
Phase 6, step P6.1 (Seitan V2) has an open item from the Keybase admin path. It is not blocked by it: the local rules (expiry, single use, revocation, freshness) are implemented and tested. This item must be settled before P6.3 and P6.4 (invite events and links) ship, and before the e2e invite and accept test.
Branch p6-seitan (not pushed), commit 3eafe3b3 (pkgs/id/src/seitan/).
Verified by reading keybase/client (master, 2026-10-12)
- Accept message:
SigPayloadingo/teams/seitan_v2.gohas the fieldsstage,uid,eldest_seqno,ctime,invite_id,version, in that order. Ouraccept::messagematches. - Encoding:
kbcrypto.CodecHandle()sets onlyWriteExt.keybase/go-codecwrites positive integers in their smallest form and strings as fixstr below 32 bytes, then str8. Our golden test assumes the same. - Signature:
kbcrypto.NaclSigningKeyPrivate.Signis plained25519.Signover the payload, with no domain prefix. Keybase verifies withed25519.Verify. We verify strictly, which accepts a subset of what Keybase accepts. Honest signers are unaffected. ctimeunit: V2 is milliseconds (handler.go, "For V2 this is ms since the epoch"). V1 and invite links are seconds.- Admin V2 check:
verifySeitanSingleV2(go/teams/handler.go) verifies the signature over the message rebuilt from the server-suppliedUnixCTime. It has no freshness check onctime.
Not verified: what must be checked
- Server side (closed source). The
team/seitan_v2endpoint receivessig,now, andinvite_id, and forwardsUnixCTimeto the admin's handler. The signature coversctime, so the server cannot alter it without failing the check. Still unknown: what the server does with a withheld or replayed accept, and whether it keeps any state that the admin relies on. This cannot be checked from the client repo. - Keybase's own V2 invites are old-style.
Team.InviteSeitanV2(go/teams/teams.go) creates anSCTeamInvitewith only type, name, and ID.IsNewStyleInviteisinvite.MaxUses != nil(go/teams/chain.go), so the admin path does not check expiry or a use count for these invites.CanConsumeInviteandConsumeInviteByID(go/teams/transactions.go) check only the completed-invite marker within one transaction. Expiry and single use in our design are our rules, not Keybase's. Still to check: how a V2 invite stays single-use across transactions (the chain's stored state). Until that is settled, Keybase must not be cited as the reference for single use or expiry. - No accept sample from a real client. No Keybase test vector covers an accept or a signed accept. Capture one accept (
uid,eldest_seqno,ctime,invite_id, and the signature) from a real Keybase client and check thatseitan::accept::verifyaccepts its bytes. This is the only check of the accept bytes beyond the source reading. - V3 (invite links). The invite-link path (
verifySeitanSingleInvitelink, seconds-basedctime, AKey) is out of scope for P6.1 and is not checked here.
What the code assumes until these are checked
- The accept message is Keybase's field set and encoding, as read above.
- Expiry and single use are local rules, enforced by the admin's node on its own invite state, not by Keybase.
- The freshness window (N23) is a local rule, not part of the accept bytes.
Reference: the S9 spike doc/2026-10-11T03-44-33Z_design_groups_events_delegation/spikes/s9-seitan/RESULTS.md, and the phase record doc/2026-10-12T19-11-31Z_phase_6_invites_pull_cli/.
Acceptance criteria
- A real Keybase client accept sample (uid, eldest_seqno, ctime, invite_id, signature) is captured and
seitan::accept::verifyis shown to accept its bytes (golden test added). - The single-use question for old-style V2 invites across transactions is settled from keybase/client chain state, or Keybase is explicitly no longer cited as the reference for single use/expiry.
- The server-side unknowns (withheld/replayed accepts, server state) are documented as accepted unknowns with a stated rationale, since the closed-source endpoint cannot be checked from the client repo.
- This item is closed out before P6.3/P6.4 (invite events and links) ship, per the body's constraint.
Metadata
Metadata
Assignees
Labels
app/idPackage/app: id (pkgs/ or apps/ in this repo)Package/app: id (pkgs/ or apps/ in this repo)effort/mMedium: expected under 1 day of workMedium: expected under 1 day of workkind/infrastructureInfrastructure / host-portability workInfrastructure / host-portability workmeta/enrichedIntake review done: acceptance criteria, links, and normalized labels addedIntake review done: acceptance criteria, links, and normalized labels addedmode/onlineFully doable remotely: design, config, code, cloudFully doable remotely: design, config, code, cloudpriority/normalOrdinary priority (the default)Ordinary priority (the default)queue/blockedQueue or user escalation stateQueue or user escalation statequeue/queuedHas a queued task in the Supabase agent queueHas a queued task in the Supabase agent queuesource/humanFiled directly by a humanFiled directly by a humanstatus/blockedQueue or user escalation stateQueue or user escalation stateuser/escalatedQueue or user escalation stateQueue or user escalation state
Activity
docs(id): phase 6 seitan and freshness [phase 6]
dezren39 commentedon Oct 24, 2026
id train triage (2026-10-24): needs-decision — project owner: settle the Keybase server-side admin path before P6.3 (local rules are implemented and tested).
dezren39 commentedon Oct 27, 2026
Intake review
Phase 6 (P6.1) verification item for Seitan V2. The client-side reading is thorough and the local rules are implemented/tested per the body, but three checks remain open by the body's own account: server-side behavior (closed source — document as accepted unknown), old-style V2 invite single-use across transactions, and a real-client accept sample. Still live, and it gates P6.3/P6.4.
Risks: Citing Keybase as the reference for expiry/single-use before check 2 settles would bake a wrong assumption into P6.3 invite events.
Suggested approach: Capture the real accept sample first (it is the only end-to-end check of the verify path), then settle the chain-state question from keybase/client, then record the server-side unknowns as accepted with rationale.
Related: Phase 6 PR #197 (invites, pull, CLI) in this repo; implementation on branch p6-seitan, pkgs/id/src/seitan/.
Enriched by the fleet monitor (intake pass): labels normalized and acceptance criteria appended to the body. This is triage only — no work has been started.
9 remaining items
dezren39 commentedon Nov 1, 2026
agent-note:v1
{"kind":"pickup","task_id":4803,"worker":"repo-worker-code","lane":"openchamber-scheduled-lane","stage":"claimed","note":"OpenChamber scheduled lane pickup 2026-11-01: issue #194 remains open; PR #197 is merged; no active PR for this residual verification task and no hard-stop labels. Revalidating acceptance items before edits."}
docs(seitan): qualify Keybase V2 single-use evidence (#194)
dezren39 commentedon Nov 1, 2026
agent-note:v1
{"kind":"blocked","task_id":4803,"worker":"repo-worker-code","lane":"openchamber-scheduled-lane","stage":"blocked","note":"Escalated to Drew: an authorized real Keybase V2 accept capture is required. The isolated official-client signup attempt did not provision an account (exit 2; whoami empty). Please provide the signed accept fixture and invite public key on #194; do not include the invite token or credentials. Documentation PR #3768 records the settled chain-state result and accepted server-side unknowns."}
Findings — PR #3768
Old-style V2 single-use is settled for the normal sequential client flow. At keybase/client commit 952e87e,
InviteSeitanV2creates an invite withoutMaxUsesor expiry. Old-style completion is emitted byCanConsumeInvite/ConsumeInviteByID, persisted asCOMPLETEDchain state, and excluded from later active-invite lookups; the normal handler repolls before consuming (chain state, active lookups, handler). This establishes sequential use after the accepting transaction commits and refreshed state is observed—not atomic exclusion of concurrent/stale handlers or server-side replay behavior.Server-side unknowns are accepted. The
team/seitan_v2service is closed source; whether it withholds/replays accepts or relies on its own state is not established by the client. Local admission verifies the signed proof and applies local expiry, freshness, and single-use state, so it does not rely on undocumented endpoint state. Withholding may still delay or deny service.Real-client sample — Drew action required. This laptop had no installed Keybase client/account. I verified the official Linux client package signature, extracted the CLI under an isolated temporary home, and tried
signup --no-email; it exited 2 andwhoamiremained empty. There is no authorized account/team here to perform an actual accept, and no synthetic sample was made.Please use a Keybase account with access to a test team and a second authorized account to create and accept a Seitan V2 invite. Then provide the real
uid,eldest_seqno,ctime,invite_id, exact signed msgpack bytes, signature, and that invite's public verification key so we can add theseitan::accept::verifygolden test. Do not post the invite token or account credentials. The task is blocked/escalated and this issue remains open pending that fixture.Merge pull request #3768 from developing-today/queue/4803-194-keybase…