Doramagic Project Pack · Human Manual

mcp-proxy

The startHTTPServer function in src/startHTTPServer.ts exposes an MCP server (typically stdio-based) over HTTP, supporting both streamable HTTP (/mcp) and legacy SSE (/sse) endpoints. It i...

Introduction and Architecture

Related topics: HTTP Server: CORS, Authentication, and Stateless Mode, Stdio Server, CLI, and Public Tunnel

Section Related Pages

Continue reading this section for the full explanation and source context.

Section proxyServer — the message router

Continue reading this section for the full explanation and source context.

Section StdioClientTransport — process bridge

Continue reading this section for the full explanation and source context.

Section InMemoryEventStore — resumability buffer

Continue reading this section for the full explanation and source context.

Related topics: HTTP Server: CORS, Authentication, and Stateless Mode, Stdio Server, CLI, and Public Tunnel

Introduction and Architecture

Purpose and Scope

mcp-proxy is a TypeScript proxy that bridges Model Context Protocol (MCP) servers using stdio transport with clients that speak Streamable HTTP or Server-Sent Events (SSE). It enables any stdio-based MCP server — including those distributed as npx packages or local scripts — to be exposed over HTTP endpoints such as /mcp and /sse, making them consumable by browser-based IDEs, containerized deployments, and remote MCP clients.

The project is dual-published to both npm and the JSR registry, distributed as pure ESM, and exposes a single CLI binary (mcp-proxy) plus a programmatic API. The description in package.json states: *"A TypeScript SSE proxy for MCP servers that use stdio transport."* The package is MIT-licensed (see package.json) and depends only on the official @modelcontextprotocol/sdk and the pipenet library for stream piping (see package.json).

The README.md notes that the proxy is the same component used internally by FastMCP to enable streamable HTTP and SSE for its own servers.

High-Level Architecture

The proxy sits between a downstream MCP client and an upstream stdio-only MCP server, translating between transport layers without altering MCP semantics. The core data flow is:

flowchart LR
    A[HTTP/SSE Client] -->|Streamable HTTP / SSE| B(startHTTPServer)
    B -->|JSON-RPC messages| C{proxyServer}
    C -->|MCP requests| D(Client)
    D -->|stdio frames| E[StdioClientTransport]
    E -->|stdin/stdout| F[Child MCP Server Process]
    F -->|stdout frames| E
    E -->|JSON-RPC responses| D
    D --> C
    C --> B
    B -->|HTTP / SSE frames| A

In the reverse direction, the same proxy can be started as a stdio server that connects to an upstream HTTP/SSE MCP server. The test suite in src/startStdioServer.test.ts exercises this mode by forking an SSE+StreamableHTTP-compatible SDK example and verifying bidirectional message flow.

Core Modules

`proxyServer` — the message router

src/proxyServer.ts exports the proxyServer function, which wires a downstream Client to an upstream Server. It conditionally registers request handlers (tools/list, tools/call, resources/read, prompts/get, complete, subscribe, unsubscribe, etc.) only for capabilities the upstream server advertises, and forwards logging notifications in both directions when serverCapabilities.logging is present. This conditional registration — visible in handlers such as ListToolsRequestSchema, CallToolRequestSchema, and ReadResourceRequestSchema in src/proxyServer.ts — ensures the proxy never claims capabilities the upstream does not have.

`StdioClientTransport` — process bridge

src/StdioClientTransport.ts is a fork of the SDK's StdioClientTransport. It spawns a child process (the upstream MCP server) with the configured command, args, cwd, env, and shell options, then pipes JSON-RPC messages over its stdin/stdout. Stderr handling defaults to inherit (matching Node's child_process.spawn semantics), and a JSONFilterTransform strips non-JSON noise from the output stream. Events such as process spawn, exit, and error are surfaced through the onEvent callback.

`InMemoryEventStore` — resumability buffer

src/InMemoryEventStore.ts implements the SDK's EventStore interface using an in-memory Map. It assigns monotonic event IDs (a stream ID plus a timestamp+counter suffix) and supports replayEventsAfter() so a streamable-HTTP client can resume a dropped SSE connection by replaying missed events. The file header notes that the store is intended for examples and testing rather than production persistence.

Public entry point

src/index.ts (declared as the JSR export in jsr.json) re-exports proxyServer, startHTTPServer, startStdioServer, the StdioServerParameters and TransportEvent types, and the authentication helpers, providing a single import surface for programmatic users.

Authentication and Configuration

src/authentication.ts defines the AuthConfig interface and the AuthenticationMiddleware class. The middleware supports two modes:

ModeMechanismTrigger
API keyX-API-Key header validation against config.apiKeyAny non-empty config
OAuth BearerAuthorization: Bearer … validated by a user-supplied authenticate callbackconfig.oauth present
Scope challengeWWW-Authenticate response with error="insufficient_scope", scope=, and resource_metadata=getScopeChallengeResponse()

The tests in src/authentication.test.ts verify that the WWW-Authenticate header is correctly ordered and escaped, and that 403 responses include the insufficient_scope JSON-RPC error code -32001.

Known Issues and Community Notes

Several regressions and edge cases documented in the issue tracker have direct architectural implications:

  • Request-handling order regression (6.x): per issue #61, onUnhandledRequest was consuming the body before MCP handlers could read it, causing POST /mcp to 404. This was addressed by the skip onUnhandledRequest for MCP protocol endpoints fix in v6.4.6.
  • Auth vs. health checks (issue #58): GET /health and GET /ready previously returned 401 when apiKey was enabled. The move onUnhandledRequest before auth middleware fix shipped in v6.4.5 restores reachability for container probes.
  • Session timeout regression (issue #57): the SDK bump in v6.4.4 aligned idle session timeouts with Node's 5-second keepAliveTimeout, surfacing "Session not found" errors.
  • Malformed request URLs (issue #66): a request target of // triggers an uncaught ERR_INVALID_URL that crashes the process.
  • SSE → Streamable HTTP bridging (issue #20): a long-standing open feature request to use mcp-proxy to convert existing SSE servers into Streamable HTTP endpoints.

See Also

  • Authentication Middleware — deep dive into AuthConfig, Bearer validation, and scope challenges
  • HTTP Server — endpoint layout, CORS defaults, and the /mcp + /sse route table
  • Stdio Transport — child-process lifecycle, stderr handling, and shell mode
  • Changelog — version-by-version regression notes

Source: https://github.com/sparfenyuk/mcp-proxy / Human Manual

HTTP Server: CORS, Authentication, and Stateless Mode

Related topics: Introduction and Architecture, Stdio Server, CLI, and Public Tunnel, Troubleshooting, Known Issues, and Release History

Section Related Pages

Continue reading this section for the full explanation and source context.

Section API Key

Continue reading this section for the full explanation and source context.

Section OAuth 2.0 Bearer Tokens

Continue reading this section for the full explanation and source context.

Section Scope Challenge (Step-Up Auth)

Continue reading this section for the full explanation and source context.

Related topics: Introduction and Architecture, Stdio Server, CLI, and Public Tunnel, Troubleshooting, Known Issues, and Release History

HTTP Server: CORS, Authentication, and Stateless Mode

Overview

The startHTTPServer function in src/startHTTPServer.ts exposes an MCP server (typically stdio-based) over HTTP, supporting both streamable HTTP (/mcp) and legacy SSE (/sse) endpoints. It is the public programmatic entry point — re-exported from src/index.ts:6 — and powers the FastMCP streamable HTTP/SSE feature. The HTTP server orchestrates three cross-cutting concerns:

  • CORS — browser-friendly access from MCP web clients
  • Authentication — API key and OAuth 2.0 bearer token validation
  • Stateless mode — server-less transport suitable for short-lived, request-scoped sessions

These three areas have been the focus of multiple bug fixes (see v6.4.5, v6.4.6, v6.5.0, v6.5.1) and are the source of the most common user-reported issues.

CORS Configuration

CORS is enabled by default and is fully configurable. The default policy, defined in src/startHTTPServer.ts:24-31, is permissive but explicit:

FieldDefault Value
allowedHeadersContent-Type, Authorization, Accept, Mcp-Session-Id, Mcp-Protocol-Version, Last-Event-Id
credentialstrue
exposedHeaders["Mcp-Session-Id"]
methods["GET", "POST", "OPTIONS"]
origin"*"

The cors option accepts a boolean or a CorsOptions object (the type is exported from src/index.ts:5). When false, CORS is fully disabled; when true or undefined, defaults apply; otherwise user values are merged with the defaults (src/startHTTPServer.ts:33-46). The actual Access-Control-Allow-* headers are written by the corsMiddleware function (src/startHTTPServer.ts:48-110).

A common pattern is to restrict origins to a known allowlist while keeping wildcard headers:

await startHTTPServer({
  createServer: async () => { /* ... */ },
  port: 3000,
  cors: {
    origin: ["https://myapp.com", "https://admin.myapp.com"],
    allowedHeaders: "*",
  },
});

CLI flag: The --corsAddAllowedHeader flag, added in v6.5.0, appends to the default Access-Control-Allow-Headers list — useful when a custom auth header blocks browser preflight under --apiKey. For broader overrides (origin allowlist, wildcard headers, disabling CORS), use the programmatic cors option. Source: README.md

Migration note (5.5.6 → 5.9.0+): Versions older than 5.9.0 sent wildcard Access-Control-Allow-Headers automatically. To preserve that behavior, explicitly set cors: { allowedHeaders: "*" }. Source: README.md

Authentication

Authentication is delegated to AuthenticationMiddleware in src/authentication.ts:9-. The middleware supports two strategies, configured via the AuthConfig interface (src/authentication.ts:1-13).

API Key

Passing apiKey to startHTTPServer causes the middleware to require an X-API-Key header on every request. Requests with missing or mismatched keys receive a 401 with an optional WWW-Authenticate header when OAuth is also configured. Source: src/authentication.test.ts:32-40

OAuth 2.0 Bearer Tokens

The oauth sub-config (src/authentication.ts:2-12) covers the protected-resource metadata model. The middleware builds a WWW-Authenticate challenge that includes error, error_description, realm, and resource_metadata fields. When protectedResource.resource is set, the resource URL is suffixed with /.well-known/oauth-protected-resource. Source: src/authentication.test.ts:73-90

Scope Challenge (Step-Up Auth)

Implemented in response to issue #49, getScopeChallengeResponse returns a 403 with a WWW-Authenticate: Bearer error="insufficient_scope" ... header listing the required scopes. The HTTP server detects scope-challenge errors thrown during request handling and short-circuits to this response. Source: src/startHTTPServer.ts:130-145

Request Flow & Known Issues

flowchart TD
    A[HTTP Request] --> B{Path matches MCP endpoint?}
    B -- Yes --> C[authMiddleware.validateRequest]
    B -- No --> D[onUnhandledRequest or /ping /health /ready]
    C -- Valid --> E[StreamableHTTPServerTransport.handleRequest]
    C -- Invalid --> F[401 with WWW-Authenticate]
    D -- Health/Ready --> G[Return 200 OK]
    D -- Other --> H[Custom handler or 404]
    E --> I{Error type?}
    I -- ScopeChallenge --> J[403 insufficient_scope]
    I -- AuthError --> F
    I -- Other --> K[500]
Community issues resolved in this flow:
- #58/health and /ready returned 401 under apiKey because the auth middleware ran before onUnhandledRequest. Fixed in v6.4.5 by moving onUnhandledRequest before auth (commit 4c532c3).
- #61 — FastMCP's httpStream POST /mcp returned 404 in 6.x because onUnhandledRequest consumed the request body. Fixed in v6.4.6 by skipping onUnhandledRequest for MCP protocol endpoints (commit a2243b0).

Stateless Mode

Setting stateless: true (CLI: --stateless) tells startHTTPServer not to track MCP sessions. The server uses StreamableHTTPServerTransport with sessionIdGenerator: undefined, so no Mcp-Session-Id is issued. Source: src/startHTTPServer.ts:101-130

Key behaviors:

  • authenticate runs on every request instead of once per session.
  • Stateless clients without a sessionId now receive 405 for non-initialize requests — a fix introduced in v6.5.1 via commit bf7d464.
  • When no eventStore is supplied, InMemoryEventStore is used so that StreamableHTTPServerTransport can replay missed SSE events to late subscribers. Source: src/InMemoryEventStore.ts

The stateless path is verified by tests in src/startHTTPServer.test.ts:150-220 for OAuth bearer token flows and authentication-error handling.

Community issues:
- #57 — v6.4.4 bumped @modelcontextprotocol/sdk to ^1.27.1 (see package.json), causing sessions to be destroyed after 5s idle (Node's default keepAliveTimeout). Stateless mode sidesteps this by avoiding session tracking entirely.
- #55 — Python stdio servers occasionally fail with "Expected server to respond to ping". Stateless mode is recommended for such short-lived containers because there is no persistent MCP session to keep alive.

Summary

The HTTP server in mcp-proxy is a thin but configurable layer over the MCP SDK's StreamableHTTPServerTransport. CORS defaults favor browser compatibility, authentication supports both static API keys and OAuth 2.0 with scope challenges, and stateless mode is the recommended path for serverless deployments. Most issues filed against this code (health endpoints, body consumption, session lifetime) are now resolved in the 6.4.5 → 6.5.1 release window.

See Also

Source: https://github.com/sparfenyuk/mcp-proxy / Human Manual

Stdio Server, CLI, and Public Tunnel

Related topics: Introduction and Architecture, HTTP Server: CORS, Authentication, and Stateless Mode

Section Related Pages

Continue reading this section for the full explanation and source context.

Related topics: Introduction and Architecture, HTTP Server: CORS, Authentication, and Stateless Mode

Stdio Server, CLI, and Public Tunnel

The mcp-proxy project exposes a single executable that has three coordinated responsibilities: (1) presenting a CLI surface for launching and configuring the proxy, (2) wiring a stdio-based MCP server into the proxy by spawning it as a child process, and (3) optionally publishing the resulting HTTP/SSE endpoint through a public tunnel. This page documents how those three pieces fit together, which files implement them, and the operational caveats users most often encounter (Python unbuffered mode, Node.js --shell quirks, and subdomain availability).

Command-Line Interface

The CLI entry point is shipped through the package's bin field, which maps the mcp-proxy command to the compiled ESM bundle in dist/bin/mcp-proxy.mjs. Source: package.json ("bin": { "mcp-proxy": "dist/bin/mcp-proxy.mjs" }). The build pipeline produces this artifact via tsdown, with src/bin/mcp-proxy.ts declared as one of two entries (the other being src/index.ts). Source: package.json (tsdown.entry: ["src/index.ts", "src/bin/mcp-proxy.ts"]).

The README documents two invocation patterns that the CLI parser (yargs, listed under devDependencies) supports. The first pattern is the "simple usage" form, where every token after mcp-proxy is forwarded to the child process: npx mcp-proxy npx -y @anthropic/mcp-server-filesystem /path. The second pattern introduces the -- separator so the proxy can consume its own options (for example --port 8080 --shell) while still passing the remainder through to the child command: npx mcp-proxy --port 8080 --shell -- tsx server.js. Source: README.md ("Quickstart / Command-line"). The README also notes that the -- separator is optional when no proxy options are required, which matches how yargs parses its own argument boundary.

Public-facing options surfaced by the CLI include --port, --shell, --debug, --tunnel, and --tunnelSubdomain. When the tunnel is active, the CLI prints a line such as tunnel established at https://abcdefghij.tunnel.gla.ma once the tunnel handshake completes, and the user should rely on the actually-printed URL rather than the requested subdomain. Source: README.md ("Public Tunnel").

Stdio Server Mode

The stdio server role is implemented by src/startStdioServer.ts, which is consumed both by the CLI (when run without --port or --tunnel) and by programmatic users. In stdio mode the proxy itself is the MCP server: it reads JSON-RPC messages from its own stdin and writes responses to its own stdout, while internally talking to a downstream server through one of the available transports. Tests for this mode live in src/startStdioServer.test.ts, where fixtures such as src/fixtures/simple-stdio-proxy-server.ts are launched via StdioClientTransport to verify round-trips including notification streams. Source: src/startStdioServer.test.ts.

The child-process driver is a custom StdioClientTransport forked from the upstream TypeScript SDK's stdio.ts implementation. It accepts a command, optional args[], an env map, an optional cwd, an onEvent callback, a shell boolean, and a stderr handling mode. The header comment in the file explicitly calls out the fork origin so future maintainers know where to rebase changes. Source: src/StdioClientTransport.ts (file-level /** Forked from ... */ docblock). The transport pipes the child's stdout through a JSONFilterTransform (also maintained in this repo) so stray log lines emitted on stdout do not corrupt the MCP framing, and it exposes onEvent for lifecycle observation. Source: src/StdioClientTransport.ts (import of JSONFilterTransform; StdioServerParameters type).

A common community-reported failure in this mode is the Python "Expected server to respond to ping" timeout. The README addresses it by recommending unbuffered Python execution: either npx mcp-proxy -- python -u -m your_package.mcp_server or PYTHONUNBUFFERED=1 npx mcp-proxy -- python -m your_package.mcp_server, plus the rule that MCP stdio servers should keep stdout reserved for protocol frames and route diagnostic output to stderr. Source: README.md ("Troubleshooting Python stdio servers"). A related Node.js issue, "Unable to proxy nodejs-based MCP server" (issue #22), has been observed to silently time out; the proxy is normally the correct tool for that case, so a timeout typically indicates buffering or process-tree issues rather than a protocol mismatch.

Public Tunnel

When the CLI is started with --tunnel, the proxy arranges for the local HTTP/SSE port (the same /mcp and /sse endpoints described in the HTTP server path) to be reachable over the public internet through a tunnel. The README demonstrates the canonical invocation: npx mcp-proxy --port 8080 --tunnel -- tsx server.js. A specific subdomain can be requested with --tunnelSubdomain myapp, and the proxy prints the live URL once the handshake completes. Source: README.md ("Public Tunnel"). Because subdomains are not guaranteed, the README explicitly warns that the requested name may not be available and the user should read the actual URL from the console output rather than assuming the requested one. Source: README.md (> [!NOTE] The requested subdomain may not be available...).

The tunnel is intended for short-lived sharing, webhook testing, and remote development, not as a production ingress. Operations teams combining tunnels with apiKey authentication should be aware of the related health-endpoint regression: with apiKey enabled, GET /health and GET /ready were returning 401 before reaching onUnhandledRequest, breaking Docker HEALTHCHECK and Kubernetes probes. The fix shipped in v6.4.5 ("move onUnhandledRequest before auth middleware") and a follow-up in v6.4.6 added a guard that skips onUnhandledRequest for MCP protocol endpoints. Source: release notes for v6.4.5 and v6.4.6.

Operational Data Flow

The combined CLI → stdio → optional tunnel path can be summarized as follows.

flowchart LR
    User["User (shell)"] --> CLI["mcp-proxy CLI<br/>(src/bin/mcp-proxy.ts)"]
    CLI -->|spawns| Child["Child stdio MCP server<br/>(tsx, python -u, npx ...)"]
    CLI -->|exposes| HTTP["HTTP server<br/>/mcp + /sse"]
    CLI -->|if --tunnel| Tunnel["Public tunnel<br/>https://*.tunnel.gla.ma"]
    Child <-->|JSON-RPC over stdin/stdout| Stdio["StdioClientTransport<br/>(forked from SDK)"]
    Stdio --> Proxy["proxyServer<br/>(src/proxyServer.ts)"]
    Proxy <--> HTTP
    Remote["Remote MCP client"] --> Tunnel
    Tunnel --> HTTP

See Also

Source: https://github.com/sparfenyuk/mcp-proxy / Human Manual

Troubleshooting, Known Issues, and Release History

Related topics: HTTP Server: CORS, Authentication, and Stateless Mode, Stdio Server, CLI, and Public Tunnel

Section Related Pages

Continue reading this section for the full explanation and source context.

Section Server Crashes on Malformed Request Targets

Continue reading this section for the full explanation and source context.

Section 401 Blocking Health Probes

Continue reading this section for the full explanation and source context.

Section 404 on POST /mcp with FastMCP httpStream

Continue reading this section for the full explanation and source context.

Related topics: HTTP Server: CORS, Authentication, and Stateless Mode, Stdio Server, CLI, and Public Tunnel

Troubleshooting, Known Issues, and Release History

This page consolidates the known limitations, recurring failure modes, and version history of the mcp-proxy project. It is intended for operators and integrators who need to diagnose problems in production, evaluate upgrade paths, or understand the regression surface across recent releases. The information below is derived directly from the source tree, the test suite, and the public issue tracker referenced in the community context.

Architecture Context for Troubleshooting

mcp-proxy is a TypeScript proxy that exposes a stdio-based MCP server over streamable HTTP and SSE endpoints. The HTTP entry point is implemented in src/startHTTPServer.ts, which wires Express middleware for CORS, authentication, and a custom onUnhandledRequest fallback before delegating to the MCP StreamableHTTPServerTransport from @modelcontextprotocol/sdk. The stdio child process is managed by src/StdioClientTransport.ts, and event replay for resumable streams is provided by the in-memory store in src/InMemoryEventStore.ts. Authentication is encapsulated in src/authentication.ts and supports both apiKey and OAuth protectedResource configurations.

flowchart LR
  Client[HTTP/SSE Client] -->|request| Middleware{CORS + Auth + onUnhandledRequest}
  Middleware -->|/mcp or /sse| Transport[StreamableHTTPServerTransport]
  Transport --> Proxy[proxyServer]
  Proxy --> Stdio[StdioClientTransport]
  Stdio --> Child[Child MCP server process]
  Transport -.replay.-> EventStore[InMemoryEventStore]

This pipeline is relevant for troubleshooting because most reported issues originate in the middleware ordering, the SDK transport, or the child process boundary. Source: src/startHTTPServer.ts:1-120.

Known Issues and Failure Modes

Server Crashes on Malformed Request Targets

The HTTP server terminates the Node.js process when it receives a request whose target is //. The crash surfaces as an uncaught ERR_INVALID_URL thrown by Node's HTTP parser. The issue is reported in #66 and reproduces in production by sending a raw // request line. Mitigations should include a fronting reverse proxy that normalizes request lines or a process supervisor that restarts the service.

401 Blocking Health Probes

When apiKey authentication is configured, GET /health and GET /ready are intercepted by the auth middleware before onUnhandledRequest runs, returning 401. This breaks container orchestrator health checks. The fix shipped in v6.4.5 (commit 4c532c3, referenced in the community context) reorders the middleware so that onUnhandledRequest runs before authentication. As an interim workaround, operators can omit the apiKey for internal probe traffic. Source: src/authentication.ts:90-140, src/startHTTPServer.ts:1-120.

404 on `POST /mcp` with FastMCP httpStream

Since the 6.x series, FastMCP's httpStream transport returns 404 for POST /mcp because the onUnhandledRequest hook consumes the request body before the MCP transport handlers run. The fix shipped in v6.4.6 (commit a2243b0) skips onUnhandledRequest for MCP protocol endpoints. Issue #61 documents the regression from the 5.x line.

Session Regression in v6.4.4

Bumping @modelcontextprotocol/sdk from ^1.24.3 to ^1.27.1 caused MCP sessions to be destroyed after the Node.js default keepAliveTimeout of roughly 5 seconds. Clients receive Session not found on subsequent tool calls. Issue #57 tracks the regression. Workarounds include pinning to the previous SDK version or tuning server.keepAliveTimeout in deployment manifests.

Python `stdio` Servers Failing Ping

Python MCP servers running under mcp-proxy may fail with Expected server to respond to ping when invoked inside containerized environments such as Glama Docker. Issue #55 attributes the failure to process startup timing and Python interpreter resolution in slim images. Adding python3 -u and explicit PYTHONUNBUFFERED=1 is the recommended mitigation.

Silent Timeout When Proxying Node Servers

Issue #22 reports that proxying Node.js-based MCP servers (for example, the everything reference server) results in silent timeouts even with --debug. The most common root cause is mismatched -- separator handling in the CLI argument parser. The README distinguishes two invocation patterns: simple usage without mcp-proxy options versus the explicit -- form, e.g. npx mcp-proxy --port 8080 --shell -- tsx server.js. Source: README.md:20-40.

ServerNotification Validation Warnings

Issue #33 reports WARNING:root:Failed to validate notification: 13 validation errors for ServerNotification originating from a Python upstream. The warning is emitted by the upstream server itself when the proxy forwards a notification that does not match the SDK's expected schema. Filtering is recommended on the upstream side rather than mutating notifications in the proxy.

License Metadata Mismatch

Issue #63 notes that package.json declares MIT while the LICENSE file contains the BSD 2-Clause text. The published JSR and npm metadata both record MIT (see package.json:20, jsr.json:1-10), so the npm/JSR distribution is MIT; downstream consumers embedding the BSD text should be aware of the discrepancy until the repository is normalized.

Release History and Upgrade Path

The most recent releases on the main branch (per package.json:1-10 and the community release notes) emphasize HTTP transport correctness, CORS configurability, and SDK compatibility.

VersionDateHighlightsRelated Issue
v6.5.12026-05-20Returns 405 for stateless clients without sessionId
v6.5.02026-05-12Adds --corsAddAllowedHeader CLI flag
v6.4.62026-04-13Skips onUnhandledRequest for MCP protocol endpoints#61
v6.4.52026-04-08Moves onUnhandledRequest before auth middleware#58
v6.4.42026-03-13Updates MCP SDK (introduces session regression)#57

Operators pinned on v6.4.4 should consider v6.4.5 or later to recover the session keep-alive behavior, and at minimum v6.4.6 to restore POST /mcp handling for FastMCP transports. The --corsAddAllowedHeader flag introduced in v6.5.0 is the recommended path for clients that send custom headers under CORS preflight, which is otherwise rejected by the default allow-list. Source: README.md:1-40, src/startHTTPServer.ts:1-120.

Diagnostic Checklist

  1. Reproduce the failure with --debug and capture the stderr stream for uncaught exception traces (relevant for #66).
  2. Verify the CLI invocation uses the documented -- separator when mcp-proxy options are present. Source: README.md:20-40.
  3. If health checks fail, confirm the proxy version is at least v6.4.5 so that onUnhandledRequest precedes auth. Source: src/authentication.ts:90-140.
  4. For Python upstream servers, set PYTHONUNBUFFERED=1 and invoke with python3 -u to avoid ping timeouts. Source: src/StdioClientTransport.ts:1-60.
  5. When integrating FastMCP httpStream, upgrade to v6.4.6 or later to avoid the POST /mcp 404 regression. Source: src/InMemoryEventStore.ts:1-40.

See Also

Source: https://github.com/sparfenyuk/mcp-proxy / Human Manual

Doramagic Pitfall Log

Source-linked risks stay visible on the manual page so the preview does not read like a recommendation.

high Installation risk requires verification

May increase setup, validation, or first-run risk for the user.

high Security or permission risk requires verification

May increase setup, validation, or first-run risk for the user.

medium Installation risk requires verification

May increase setup, validation, or first-run risk for the user.

medium Configuration risk requires verification

May increase setup, validation, or first-run risk for the user.

Doramagic Pitfall Log

Found 11 structured pitfall item(s), including 2 high/blocking item(s). Top priority: Installation risk - Installation risk requires verification.

1. Installation risk: Installation risk requires verification

  • Severity: high
  • Finding: Project evidence flags a installation risk. Review the linked source before relying on this workflow.
  • User impact: May increase setup, validation, or first-run risk for the user.
  • Recommended check: Reproduce the official install and quickstart path in an isolated environment.
  • Evidence: community_evidence:github | https://github.com/sparfenyuk/mcp-proxy/issues/168

2. Security or permission risk: Security or permission risk requires verification

  • Severity: high
  • Finding: Project evidence flags a security or permission risk. Review the linked source before relying on this workflow.
  • User impact: May increase setup, validation, or first-run risk for the user.
  • Recommended check: Reproduce the official install and quickstart path in an isolated environment.
  • Evidence: community_evidence:github | https://github.com/sparfenyuk/mcp-proxy/issues/108

3. Installation risk: Installation risk requires verification

  • Severity: medium
  • Finding: Project evidence flags a installation risk. Review the linked source before relying on this workflow.
  • User impact: May increase setup, validation, or first-run risk for the user.
  • Recommended check: Reproduce the official install and quickstart path in an isolated environment.
  • Evidence: community_evidence:github | https://github.com/sparfenyuk/mcp-proxy/issues/224

4. Configuration risk: Configuration risk requires verification

  • Severity: medium
  • Finding: Project evidence flags a configuration risk. Review the linked source before relying on this workflow.
  • User impact: May increase setup, validation, or first-run risk for the user.
  • Recommended check: Reproduce the official install and quickstart path in an isolated environment.
  • Evidence: capability.host_targets | https://github.com/sparfenyuk/mcp-proxy

5. Capability evidence risk: Capability evidence risk requires verification

  • Severity: medium
  • Finding: README/documentation is current enough for a first validation pass.
  • User impact: May increase setup, validation, or first-run risk for the user.
  • Recommended check: Reproduce the official install and quickstart path in an isolated environment.
  • Evidence: capability.assumptions | https://github.com/sparfenyuk/mcp-proxy

6. Maintenance risk: Maintenance risk requires verification

  • Severity: medium
  • Finding: Project evidence flags a maintenance risk. Review the linked source before relying on this workflow.
  • User impact: May increase setup, validation, or first-run risk for the user.
  • Recommended check: Reproduce the official install and quickstart path in an isolated environment.
  • Evidence: community_evidence:github | https://github.com/sparfenyuk/mcp-proxy/issues/214

7. Maintenance risk: Maintenance risk requires verification

  • Severity: medium
  • Finding: Project evidence flags a maintenance risk. Review the linked source before relying on this workflow.
  • User impact: May increase setup, validation, or first-run risk for the user.
  • Recommended check: Reproduce the official install and quickstart path in an isolated environment.
  • Evidence: evidence.maintainer_signals | https://github.com/sparfenyuk/mcp-proxy

8. Security or permission risk: Security or permission risk requires verification

  • Severity: medium
  • Finding: no_demo
  • User impact: May increase setup, validation, or first-run risk for the user.
  • Recommended check: Reproduce the official install and quickstart path in an isolated environment.
  • Evidence: downstream_validation.risk_items | https://github.com/sparfenyuk/mcp-proxy

9. Security or permission risk: Security or permission risk requires verification

  • Severity: medium
  • Finding: no_demo
  • User impact: May increase setup, validation, or first-run risk for the user.
  • Recommended check: Reproduce the official install and quickstart path in an isolated environment.
  • Evidence: risks.scoring_risks | https://github.com/sparfenyuk/mcp-proxy

10. Maintenance risk: Maintenance risk requires verification

  • Severity: low
  • Finding: issue_or_pr_quality=unknown。
  • User impact: May increase setup, validation, or first-run risk for the user.
  • Recommended check: Reproduce the official install and quickstart path in an isolated environment.
  • Evidence: evidence.maintainer_signals | https://github.com/sparfenyuk/mcp-proxy

11. Maintenance risk: Maintenance risk requires verification

  • Severity: low
  • Finding: release_recency=unknown。
  • User impact: May increase setup, validation, or first-run risk for the user.
  • Recommended check: Reproduce the official install and quickstart path in an isolated environment.
  • Evidence: evidence.maintainer_signals | https://github.com/sparfenyuk/mcp-proxy

Source: Doramagic discovery, validation, and Project Pack records

Community Discussion Evidence

These external discussion links are review inputs, not standalone proof that the project is production-ready.

Sources 12

Count of project-level external discussion links exposed on this manual page.

Use Review before install

Open the linked issues or discussions before treating the pack as ready for your environment.

Community Discussion Evidence

Doramagic exposes project-level community discussion separately from official documentation. Review these links before using mcp-proxy with real data or production workflows.

Source: Project Pack community evidence and pitfall evidence