Found by Vera (Connectors 69447), ruled by Wren (69450) during the C4 run on 2026-09-18: cli/src/lib/adapters/pi.js resolveMcpServers drops url-transport entries and pi-commonly-mcp.mjs speaks only stdio, while the daemon delivers the grant broker (/api/mcp/grants/<grantId>, ADR-001 tool broker) as an HTTP MCP server. Result: a pi seat can be in a grant's audience and hold the grant, and have no github.* tool to call. c4-smoke was moved to the claude adapter for the run.
Fix. Teach the bridge Streamable HTTP: for an entry with url, POST JSON-RPC (initialize, tools/list, tools/call) to the URL with the seat's runtime token as Authorization: Bearer (the same header the broker's agentRuntimeAuth reads), Accept: application/json, text/event-stream, and parse either a JSON body or the first data: SSE frame — routes/mcpGrants.ts uses the SDK's StreamableHTTPServerTransport, so both shapes occur. resolveMcpServers keeps url entries (placeholders substituted in url and headers too). Test against mcpGrants.test.js's transport with a fake broker.
Until then the runbook's rule stands: a seat that must use a room grant runs on claude or codex, not pi.
Found by Vera (Connectors 69447), ruled by Wren (69450) during the C4 run on 2026-09-18:
cli/src/lib/adapters/pi.jsresolveMcpServersdrops url-transport entries andpi-commonly-mcp.mjsspeaks only stdio, while the daemon delivers the grant broker (/api/mcp/grants/<grantId>, ADR-001 tool broker) as an HTTP MCP server. Result: a pi seat can be in a grant's audience and hold the grant, and have nogithub.*tool to call. c4-smoke was moved to the claude adapter for the run.Fix. Teach the bridge Streamable HTTP: for an entry with
url, POST JSON-RPC (initialize,tools/list,tools/call) to the URL with the seat's runtime token asAuthorization: Bearer(the same header the broker'sagentRuntimeAuthreads),Accept: application/json, text/event-stream, and parse either a JSON body or the firstdata:SSE frame —routes/mcpGrants.tsuses the SDK'sStreamableHTTPServerTransport, so both shapes occur.resolveMcpServerskeeps url entries (placeholders substituted inurlandheaderstoo). Test againstmcpGrants.test.js's transport with a fake broker.Until then the runbook's rule stands: a seat that must use a room grant runs on claude or codex, not pi.