Skip to content

OAuthClientProvider add prefix url for MCP Starlette Mounted endpoints to correctly route .well-known metadata discovery #1751

@abneetwats24

Description

@abneetwats24

Description

I am using Starlette mounting

hr_policy_mcp.settings.streamable_http_path = "/hr-policy"
math_mcp.settings.streamable_http_path = "/math"
main_server = Starlette(
        routes=[
            Mount("/hr-policy", app=hr_policy_mcp.streamable_http_app()),
            Mount("/math", app=math_mcp.streamable_http_app()),
        ],
        lifespan=combined_lifespan,
    )
main_server = CORSMiddleware(
        main_server,
        allow_origins=["*"],  # Configure appropriately for production
        allow_methods=["GET", "POST", "DELETE"],  # MCP streamable HTTP methods
        expose_headers=["Mcp-Session-Id"],
    )

With this I am getting 404 for Metadata Discovery

mcp-server  | INFO:     172.18.0.1:54902 - "GET /hr-policy/hr-policy HTTP/1.1" 401 Unauthorized
mcp-server  | INFO:     172.18.0.1:54902 - "GET /favicon.ico HTTP/1.1" 404 Not Found
mcp-server  | INFO:     172.18.0.1:33592 - "OPTIONS /hr-policy/hr-policy HTTP/1.1" 200 OK
mcp-server  | INFO:     172.18.0.1:33592 - "POST /hr-policy/hr-policy HTTP/1.1" 401 Unauthorized
mcp-server  | INFO:     172.18.0.1:42520 - "OPTIONS /.well-known/oauth-protected-resource/hr-policy/hr-policy HTTP/1.1" 400 Bad Request
mcp-server  | INFO:     172.18.0.1:42520 - "GET /.well-known/oauth-protected-resource/hr-policy/hr-policy HTTP/1.1" 404 Not Found
mcp-server  | INFO:     172.18.0.1:42520 - "OPTIONS /.well-known/oauth-protected-resource HTTP/1.1" 400 Bad Request
mcp-server  | INFO:     172.18.0.1:42520 - "GET /.well-known/oauth-protected-resource HTTP/1.1" 404 Not Found
mcp-server  | INFO:     172.18.0.1:42520 - "OPTIONS /.well-known/oauth-authorization-server HTTP/1.1" 400 Bad Request
mcp-server  | INFO:     172.18.0.1:42520 - "GET /.well-known/oauth-authorization-server HTTP/1.1" 404 Not Found

And I can see .well-known are serving on
http://127.0.0.1:3000/hr-policy/.well-known/oauth-protected-resource

http://127.0.0.1:3000/math/.well-known/oauth-protected-resource

Both provides same authorization_servers url as I am using same for both: possible having different for different realms and mounts

{"resource":"http://127.0.0.1:3000/","authorization_servers":["http://192.**.10.7:5555/realms/**testrealm"],"scopes_supported":["mcp:tools"],"bearer_methods_supported":["header"]}

Workaround
Currently I am doing Monkeypatches for url prefix fix, complete code here

import mcp.client.auth.oauth2
from mcp.client.auth import OAuthClientProvider
mcp.client.auth.oauth2.build_protected_resource_metadata_discovery_urls = _masked_build_protected_resource_metadata_discovery_urls
OAuthClientProvider._perform_authorization = _masked_perform_authorization

Can the above be also handled with the OAuthClientProvider like I can just pass in prefix mounts of mcp?

As even I have: MCP Server url as: http://127.0.0.1:3000/math/math
It is doing Metadata Discovery for base url.

References

No response

Metadata

Metadata

Assignees

No one assigned

    Labels

    No labels
    No labels

    Type

    No type

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions