Surface S1 from the graduated Fleet Manager design record D#15249 requires explicit operator/control-plane viewer admission for cross-inbox reads. #15269 landed the fail-closed mailbox adapter, and #15316 / PR #15312 land the read seam plus cockpit view while deliberately leaving the production source unwired.
The missing last mile is a trustworthy browser-to-Fleet request boundary. Until that boundary exists, wiring the real mailbox source would turn ambient local reachability into CAN_READ_INBOX_OF authority.
Live duplicate sweep: latest 20 open issues, 50 most recently updated open issues, broader GraphQL search, and the latest 30 all-state A2A messages checked at 2026-07-16T22:59Z. No equivalent active ticket exists. Closest precedents (#15185, #13172, #14988, #15283) own different boundaries.
The shipped getBootIdentity, fleetActivity, and fleetRoster JSDoc carries the same false present-tense “authenticated registryBridge” claim. Their behavior remains in scope; their prose must stop asserting a transport state that does not exist.
Loopback reachability is not authentication. Bearer possession is not viewer identity. A browser-supplied viewer id is not authority.
The Architectural Reality
RequestContextService.run() is the existing per-request identity propagation boundary. Its identity must originate at transport authentication, not from forwarded identity headers or request params.
MailboxService.listMessages() already enforces CAN_READ_INBOX_OF against the bound canonical identity. The Fleet adapter must consume that authority; it must not recreate it.
#15185 is reusable transport precedent, not a duplicate: its local MCP bearer proves possession only and deliberately creates no identity.
ADR 0019 governs any required AiConfig leaves: declarative provider-owned leaves, read at the use site; no env re-derivation, pass-along aliases, runtime mutation, or hidden defaults.
ADR 0026 §2.7 keeps the client-reachable Fleet restartAgent surface distinct from daemon-core L0 lifecycle authority. Authenticating the Fleet UI must not grant or imply that L0 envelope.
The Fix
Implement one atomic Fleet ingress trust boundary:
The cockpit launch/bootstrap path generates one process-lifetime secret from exactly 32 cryptographically random bytes, encoded as unpadded base64url. It reaches the Fleet server and browser runtime without URL, request body, log, file, database, or durable-config persistence.
Fleet binds to literal loopback and independently enforces bounded Host validation, an exact cockpit-Origin policy, and constant-time bearer verification before body parsing or dispatch.
Fleet resolves the viewer independently at trusted server bootstrap, binds it to one canonical AgentIdentity, and rejects caller-authored identity headers or params. The bearer establishes possession of the local Fleet session; it never becomes the identity fact.
Every accepted request executes inside RequestContextService.run({userId, username, agentIdentityNodeId, source}, callback) with that server-stamped viewer. Concurrent requests remain isolated.
Only after steps 1–4 are proven, wire mailboxMirrorSource to the real MailboxService.listMessages path plus a dynamic RequestContextService.getAgentIdentityNodeId() resolver. FleetControlBridge remains dependency-injected and authors no admission fact.
The one-command Fleet boot/probe path carries the same authenticated contract. An unknown, stale, or mismatched process receives a named refusal; it is never silently reused.
Any new configuration surface follows ADR 0019 and remains secret-safe. Runtime code never mutates the shared AiConfig provider.
Bearer auth, viewer binding, request context, source wiring, and boot handoff remain one lane: every partial combination is either unusable or spoofable.
aligned-with ADR 0019 and ADR 0026; no amendment. This consumes the existing config SSOT and request-context identity authority while preserving the Fleet UI versus daemon-core L0 envelope distinction.
Decision Record
NOT_NEEDED — the graduated S1 record and existing ADRs already fix the trust boundaries; this ticket composes them.
Acceptance Criteria
Fleet startup fails closed unless the listener is literal loopback, a valid process-lifetime bearer exists, and the server-side viewer resolves to one canonical AgentIdentity.
The launch path generates exactly 32 random bytes, encodes unpadded base64url, and supplies the one-run value to server and browser without URL, body, logger, SQLite, file, durable-config, or PR/test artifact persistence.
Missing, malformed, wrong, and length-mismatched bearer values return 401 before request-body parsing, method lookup, or Fleet dispatch.
Host validation remains independently enforced. Foreign/null Origin values are rejected; the exact cockpit Origin is echoed with Vary: Origin; wildcard CORS is removed. An absent Origin is accepted only with the valid bearer.
The browser client sends Authorization: Bearer … and sends no viewer-identity claim.
Authentication gates the complete FLEET_WIRE_METHODS surface. Negative tests prove unauthenticated lifecycle, registry, tenant, and credential-bearing calls produce zero side effects.
The server derives userId, username, and agentIdentityNodeId independently of request data, then wraps every admitted call in RequestContextService.run().
A delayed concurrent viewer A/B falsifier proves request context cannot leak or swap across requests.
mailboxMirrorSource is wired only after the trust boundary is active, using the dynamic bound-identity resolver and real MailboxService.listMessages.
End-to-end evidence covers: admitted read, named CAN_READ_INBOX_OF denial, unbound viewer, spoofed viewer input, cross-subject refusal, pagination, and an unauthenticated call that never reaches MailboxService.
The one-command boot/probe path proves correct-token/correct-viewer reuse and named refusal for stale, unknown, wrong-token, or wrong-viewer processes.
JSDoc and operator-facing docs describe the actual trust state. The false present-tense “authenticated registryBridge” claims are removed from the staged mailbox seam and the already-shipped getBootIdentity, fleetActivity, and fleetRoster verbs; no site asserts authentication before this boundary is live.
Any AiConfig additions satisfy ADR 0019 at the use site; tests isolate by construction and never mutate the shared provider.
Focused unit, integration, and Neural Link evidence covers the full browser → HTTP → RequestContext → MailboxService admission path.
Context
Surface S1 from the graduated Fleet Manager design record D#15249 requires explicit operator/control-plane viewer admission for cross-inbox reads. #15269 landed the fail-closed mailbox adapter, and #15316 / PR #15312 land the read seam plus cockpit view while deliberately leaving the production source unwired.
The missing last mile is a trustworthy browser-to-Fleet request boundary. Until that boundary exists, wiring the real mailbox source would turn ambient local reachability into
CAN_READ_INBOX_OFauthority.Live duplicate sweep: latest 20 open issues, 50 most recently updated open issues, broader GraphQL search, and the latest 30 all-state A2A messages checked at 2026-07-16T22:59Z. No equivalent active ticket exists. Closest precedents (#15185, #13172, #14988, #15283) own different boundaries.
The Problem
At PR #15312 head
f624d5fb32:fleetBridgeServer.mjsis loopback-only but unauthenticated, emits wildcard CORS, reads the request body, and dispatches without a trust context.installFleetBridge.mjssends onlyContent-Type.dispatchFleetRequest.mjsforwards{method, params}directly to the bridge.FLEET_WIRE_METHODSincludes lifecycle, registry, tenant, and credential-bearing operations—not merely read-only mailbox traffic.fleetMailboxMirrorAdapter.mjscorrectly refuses to claim admission without a bound request identity.getBootIdentity,fleetActivity, andfleetRosterJSDoc carries the same false present-tense “authenticated registryBridge” claim. Their behavior remains in scope; their prose must stop asserting a transport state that does not exist.Loopback reachability is not authentication. Bearer possession is not viewer identity. A browser-supplied viewer id is not authority.
The Architectural Reality
RequestContextService.run()is the existing per-request identity propagation boundary. Its identity must originate at transport authentication, not from forwarded identity headers or request params.MailboxService.listMessages()already enforcesCAN_READ_INBOX_OFagainst the bound canonical identity. The Fleet adapter must consume that authority; it must not recreate it.restartAgentsurface distinct from daemon-core L0 lifecycle authority. Authenticating the Fleet UI must not grant or imply that L0 envelope.The Fix
Implement one atomic Fleet ingress trust boundary:
AgentIdentity, and rejects caller-authored identity headers or params. The bearer establishes possession of the local Fleet session; it never becomes the identity fact.RequestContextService.run({userId, username, agentIdentityNodeId, source}, callback)with that server-stamped viewer. Concurrent requests remain isolated.mailboxMirrorSourceto the realMailboxService.listMessagespath plus a dynamicRequestContextService.getAgentIdentityNodeId()resolver.FleetControlBridgeremains dependency-injected and authors no admission fact.Bearer auth, viewer binding, request context, source wiring, and boot handoff remain one lane: every partial combination is either unusable or spoofable.
Contract Ledger
AgentIdentity; never browser-authoredFLEET_WIRE_METHODSRequestContextService.run()Decision Record impact
aligned-with ADR 0019 and ADR 0026; no amendment. This consumes the existing config SSOT and request-context identity authority while preserving the Fleet UI versus daemon-core L0 envelope distinction.Decision Record
NOT_NEEDED— the graduated S1 record and existing ADRs already fix the trust boundaries; this ticket composes them.Acceptance Criteria
AgentIdentity.Vary: Origin; wildcard CORS is removed. An absent Origin is accepted only with the valid bearer.Authorization: Bearer …and sends no viewer-identity claim.FLEET_WIRE_METHODSsurface. Negative tests prove unauthenticated lifecycle, registry, tenant, and credential-bearing calls produce zero side effects.userId,username, andagentIdentityNodeIdindependently of request data, then wraps every admitted call inRequestContextService.run().mailboxMirrorSourceis wired only after the trust boundary is active, using the dynamic bound-identity resolver and realMailboxService.listMessages.CAN_READ_INBOX_OFdenial, unbound viewer, spoofed viewer input, cross-subject refusal, pagination, and an unauthenticated call that never reaches MailboxService.getBootIdentity,fleetActivity, andfleetRosterverbs; no site asserts authentication before this boundary is live.Out of Scope
Avoided Traps
viewerIdentity, forwarded identity header, or fixed request param.fleetMailboxMirrorwhile leaving credential/lifecycle verbs ambient.Related
Parent Epic: #13015
Blocks: #15270
Related only: #15316 / PR #15312 (independently mergeable with the source inert)
Admission primitive: #15269
Transport precedent: #15185
Source record: D#15249
Origin Session ID:
019f6120-ef4d-79f0-83f5-43e6d27f36f5Retrieval Hint:
Fleet HTTP ingress local bearer viewer identity RequestContext CAN_READ_INBOX_OF mailboxMirrorSource Host Origin— Euclid (@neo-gpt) · OpenAI GPT-5.6 Sol Ultra