Add an explicit Streamable HTTP entry for environment/gateway hosts while keeping stdio registrations and default behavior. Preserve the shared provider/session owner across DELETE and replacement; fence and drain tool/completion work before handover or teardown. Bound HTTP input and plain-response admission, cancel refused bodies, join whole exchanges and asynchronous response cleanup before provider hooks, gate startup readiness, and reject queued HTTP/1.1 pipelining while retaining sequential keep-alive. Validation: 8 static/build tasks, 83 adapter tests and registry metadata pass. A real installed gh binary produces seven equivalent CLI/stdio/HTTP reports with DELETE/replacement and clean signal shutdown. Broader local native-provider/ownership failures reproduce on clean main and are documented with limitations in the PR. Co-authored-by: Edgar Arakelyan <edgar.arakelyan@scale.com> Co-authored-by: gensokyo-dev <342580529+gensokyo-dev@users.noreply.github.com>
2.0 KiB
2.0 KiB
Implementation plan
- Widen the runtime
servedependency to a transport-neutral factory that may bind asynchronously.startMcpTransportawaits it, hands it the server logger, and keeps stdio as the default; the shutdown handle type loses its stdio name. - Add
src/server/http/nodeHttpBridge.tsto turn an IncomingMessage into a web Request (headers, streamed body, abort on client close) and to pipe a web Response back with flushed headers, andsrc/server/http/serveStreamableHttp.tsto own oneMcpServerinstance and one stateful transport per session, ended byDELETEor replaced by the next client'sinitializewithout running the instance's shutdown hooks, plus plain routes, loopback Host validation, the listening log line and idempotent close. The typed listen error lives in its own module so the stdio entry never loads the listener. - Parse
--http,--hostand--portinsrc/main/mcpHttpArguments.tsfrom one schema that also renders help; resolveMCP_HOST/MCP_PORTinsrc/config/mcpHttpEndpoint.tsas aResultthat names rejected settings without their values. - Route the dispatcher to
runMcpHttpEntrypointwhen themcpentry carries--http; compose HTTP dependencies insrc/main.tswith the sharedrun()path so configuration, session, providers and shutdown stay common. - Register signals only for HTTP mode through
registerSignalShutdown, a projection ofregisterProcessShutdownwithout stdin that sets the signal exit status before the idempotent shutdown runs; stdio keeps its stdin end/close triggers. - Document the transport in docs/mcp-contracts.md and docs/cli.md, relabel the architecture diagram, and cover each boundary with adapters, dispatcher, mcp-boundary and process-boundary tests plus a Python SDK client exchange.
No new dependency is introduced: the transport, Host validation and body bound
come from the already pinned @modelcontextprotocol/server root export. Tool
contracts, catalog digests, response budgets and stdio behaviour are unchanged.