Skip to content
Merged
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
15 changes: 14 additions & 1 deletion orthocal/asgi.py
Original file line number Diff line number Diff line change
Expand Up @@ -13,6 +13,7 @@

from django.conf import settings
from django.core.asgi import get_asgi_application
from mcp.server.transport_security import TransportSecuritySettings

django_application = get_asgi_application()

Expand All @@ -24,7 +25,19 @@
# owns its own /mcp route and lifespan (which starts/stops its session
# manager's background task). Django's ASGIHandler doesn't implement the
# lifespan protocol at all, so lifespan scope is only ever handled here.
mcp_application = mcp.streamable_http_app()
#
# transport_security must be set explicitly: with no host argument, the SDK
# defaults host to '127.0.0.1' and auto-enables DNS-rebinding protection
# restricted to localhost -- fine in local dev, but it rejects every real
# request in production (Cloud Run's own hostname as the Host header,
# forwarded by the Firebase Hosting proxy in front of it, isn't on that
# allowlist). DNS-rebinding protection defends a server bound to localhost
# against a malicious webpage's JS reaching it through the browser; it
# doesn't apply to a public HTTPS API with no localhost-only trust boundary,
# so disabling it here is the correct fix, not a workaround.
mcp_application = mcp.streamable_http_app(
transport_security=TransportSecuritySettings(enable_dns_rebinding_protection=False),
)


async def application(scope, receive, send):
Expand Down