You signed in with another tab or window. Reload to refresh your session.You signed out in another tab or window. Reload to refresh your session.You switched accounts on another tab or window. Reload to refresh your session.Dismiss alert
Custom MCP connectors connected via the claude.ai web UI (mcp-proxy.anthropic.com) never refresh OAuth tokens when they expire. The proxy reconnects the SSE transport and reports success, but never calls /token or /authorize on the upstream server. The expired token is then forwarded on the next tool call, which fails — requiring a full manual reconnect daily.
Note: This was originally filed as anthropics/claude-code#52905 (labeled duplicate there) and anthropics/claude-code#46328. Re-filing here as the root cause is in the claude.ai proxy layer — anthropics/claude-ai-mcp is the correct home for this bug.
Environment
Client: claude.ai web (Team/Enterprise plan)
Connector: Custom MCP server on Azure App Service
Auth: Azure Entra ID OBO flow (external IdP)
Transport: Streamable HTTP
What did you expect to happen?
The proxy should check token expiry before forwarding tool calls and attempt a silent refresh using the stored refresh token before falling back to a re-auth prompt — standard OAuth 2.0 refresh token grant behavior already implemented in the direct HTTP path.
Steps to reproduce
Set up a custom MCP server with Azure Entra ID (external IdP) OAuth — server exposes /.well-known/oauth-authorization-server with correct authorization_endpoint, token_endpoint, and grant_types_supported: ["authorization_code", "refresh_token"]
Add the server as a custom connector in Claude.ai Settings → Connectors
Complete the OAuth flow — connector shows as Connected, tools are available
Wait for the access token to expire (~1 hour)
Attempt any tool call on the connector
Result: Tool call fails — server receives the expired Bearer token with no prior /token refresh attempt. Connector appears disconnected. User must manually reconnect daily.
Area
OAuth / Authentication
MCP Server (if applicable)
Custom server — Azure App Service (Node.js/Express, Streamable HTTP, Azure Entra ID OBO auth)
Error messages or logs
Error in Claude Web UI (Connector page)
Connection issue
Connection has expired. You can reconnect to re-authenticate.
Server logs show zero /token or /authorize requests after initial auth.
On expired token, server returns:
HTTP 401
WWW-Authenticate: Bearer realm="Azure AD", error="invalid_token", error_description="Token validation failed"
Client behavior: SSE transport reconnects successfully but no OAuth refresh is attempted.
Expired token is forwarded on next tool call → tool call fails.
Additional context
Key Observations
Fix exists for direct HTTP path — token refresh was fixed for Claude Code direct HTTP connections in ~v2.1.59. The fix has not been ported to the mcp-proxy.anthropic.com proxy path.
Server is fully spec-compliant — /.well-known/oauth-authorization-server correctly advertises token_endpoint and grant_types_supported: ["authorization_code", "refresh_token"]. On expired token, server returns 401 with WWW-Authenticate: Bearer error="invalid_token" — a compliant client should use this to trigger a refresh. Zero /token or /authorize requests reach the server after initial auth.
What happened?
What's Wrong?
Custom MCP connectors connected via the claude.ai web UI (
mcp-proxy.anthropic.com) never refresh OAuth tokens when they expire. The proxy reconnects the SSE transport and reports success, but never calls/tokenor/authorizeon the upstream server. The expired token is then forwarded on the next tool call, which fails — requiring a full manual reconnect daily.Environment
What did you expect to happen?
The proxy should check token expiry before forwarding tool calls and attempt a silent refresh using the stored refresh token before falling back to a re-auth prompt — standard OAuth 2.0 refresh token grant behavior already implemented in the direct HTTP path.
Steps to reproduce
/.well-known/oauth-authorization-serverwith correctauthorization_endpoint,token_endpoint, andgrant_types_supported: ["authorization_code", "refresh_token"]/tokenrefresh attempt. Connector appears disconnected. User must manually reconnect daily.Area
OAuth / Authentication
MCP Server (if applicable)
Custom server — Azure App Service (Node.js/Express, Streamable HTTP, Azure Entra ID OBO auth)
Error messages or logs
Additional context
Key Observations
Fix exists for direct HTTP path — token refresh was fixed for Claude Code direct HTTP connections in ~v2.1.59. The fix has not been ported to the
mcp-proxy.anthropic.comproxy path.Server is fully spec-compliant —
/.well-known/oauth-authorization-servercorrectly advertisestoken_endpointandgrant_types_supported: ["authorization_code", "refresh_token"]. On expired token, server returns401withWWW-Authenticate: Bearer error="invalid_token"— a compliant client should use this to trigger a refresh. Zero/tokenor/authorizerequests reach the server after initial auth.External IdP compounds the issue — per Claude.ai ignores authorization_endpoint and token_endpoint from OAuth metadata when MCP server uses external authorization server #82, claude.ai ignores
authorization_endpoint/token_endpointfrom OAuth metadata for external IdPs. This means both initial auth discovery AND token refresh are broken on the proxy path for Entra ID / Okta / Auth0 setups.First-party connectors unaffected — Slack, Otter etc. remain connected. Bug is specific to custom connectors via
mcp-proxy.anthropic.com.Related Issues
anthropics/claude-code#46328— same bug, claudeai-proxy transport (original report)anthropics/claude-code#52905— duplicate filed in wrong repo, labeledduplicateby maintainersauthorization_endpoint/token_endpoint/tool_resultand/attach_resourcereturn 404/400 after successful OAuth #207 — Token issued but never used after OAuth handshake