Pit record

FastMCP returns 421 Invalid Host Header behind a proxy due to DNS rebinding protection

A FastMCP/MCP Python SDK streamable-HTTP or SSE server behind a proxy/gateway/container rejecting requests with 421 Misdirected Request / Invalid Host header is DNS rebinding protection (PR #861): the Host header is not in allowed_hosts. Set allowed_hosts/allowed_origins via TransportSecuritySettings or disable the protection where another layer secures it.

Fast answer

Problem: all external requests fail with HTTP 421 Misdirected Request and 'Invalid Host header'

Root cause: FastMCP enables DNS rebinding protection that validates the request Host header against an allowed list (added in PR #861).

Fix first: Explicitly allow your hosts and origins via TransportSecuritySettings(allowed_hosts=[...], allowed_origins=[...]).

Verify: Send a proxied request after setting allowed_hosts or disabling protection.

Queries this answers

  • Guide: Resolving '421 Invalid Host Header' DNS Rebinding Protection
  • Guide: Resolving '421 Invalid Host Header' (DNS Rebinding Protection) fix
  • Guide: Resolving '421 Invalid Host Header' (DNS Rebinding Protection) root cause
  • FastMCP returns 421 Invalid Host Header behind a proxy due to DNS rebinding protection
  • FastMCP returns 421 Invalid Host Header behind a proxy due to DNS rebinding protection fix
  • FastMCP returns 421 Invalid Host Header behind a proxy due to DNS rebinding protection root cause
  • how to fix FastMCP returns 421 Invalid Host Header behind a proxy due to DNS rebinding protection
  • mcp-server host header behind proxy dns rebinding protection

Record metadata

Statusverified
Confidencehigh
Created2026-06-21
Updated2026-06-21
Last verified2026-06-21
Affected toolsmcp-server, fastmcp
Tagsmcp, fastmcp, python-sdk, streamable-http, dns-rebinding, proxy, docker, 421

Common search queries

  • fastmcp-421-invalid-host-header-dns-rebinding
  • fastmcp 421 invalid host header dns rebinding
  • FastMCP returns 421 Invalid Host Header behind a proxy due to DNS rebinding protection
  • FastMCP returns 421 Invalid Host Header behind a proxy due to DNS rebinding protection fix
  • FastMCP returns 421 Invalid Host Header behind a proxy due to DNS rebinding protection root cause
  • fastmcp
  • python-sdk
  • streamable-http
  • dns-rebinding
  • proxy
  • docker
  • mcp-server

Symptoms

  • all external requests fail with HTTP 421 Misdirected Request and 'Invalid Host header'
  • started after upgrading the MCP Python SDK / FastMCP
  • the server runs behind Nginx/Caddy/Cloudflare Tunnel/Kubernetes or binds host=0.0.0.0
  • direct localhost access works but proxied or custom-domain access does not

Environment

languagePython
frameworkFastMCP / MCP Python SDK
constraintsstreamable-HTTP or SSE transport, reverse proxy / gateway / container deployment, host bound to 0.0.0.0

Root cause

  • FastMCP enables DNS rebinding protection that validates the request Host header against an allowed list (added in PR #861).
  • Behind a proxy or when bound to 0.0.0.0, the real Host (your domain or a cluster service name) is not in the default allowed list, so the transport-security middleware returns 421.
  • There is no startup warning, so users blame their proxy config.
  • When mounting streamable_http_app()/sse_app() into Starlette/FastAPI, the FastMCP host parameter does not control the bind address but still drives the auto-enable logic.

Fix

  1. Explicitly allow your hosts and origins via TransportSecuritySettings(allowed_hosts=[...], allowed_origins=[...]).

    Recommended for production behind a gateway; ports can be wildcarded with '*'.

  2. Or disable protection for local dev / when another layer secures it: TransportSecuritySettings(enable_dns_rebinding_protection=False).

  3. Ensure the reverse proxy forwards the correct Host header to the server.

Verification

  • Send a proxied request after setting allowed_hosts or disabling protection.

    Expected: Normal MCP responses instead of 421 Invalid Host header.

Workarounds

  • Disable DNS rebinding protection when the deployment is isolated at the network layer and authenticated via OAuth.

Anti-patterns

  • Debugging the Nginx/Caddy config when the 421 comes from FastMCP transport-security middleware.
  • Expecting the FastMCP host parameter to set the bind address for a mounted app (uvicorn/gunicorn controls that).

Sources

No matching fix?

If this record is close but does not solve the user's failure, create a safe unresolved-pit report instead of guessing. Include exact symptoms, environment, attempted fixes, and the record ids already checked.