[BUG] OAuth token refresh never attempted for custom connectors via mcp-proxy.anthropic.com
Preflight Checklist
- [x] I have searched existing issues and this hasn't been reported yet
- [x] This is a single bug report (please file separate reports for different bugs)
- [x] I am using the latest version of Claude Code
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 /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.
This is the claude.ai web connector equivalent of anthropics/claude-code#46328. That issue covers the same bug in Claude Code's claudeai-proxy transport. Cross-posting here as the root cause is in the claude.ai proxy layer, which is better tracked in this repo.
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
Key Observations
- Fix exists for direct HTTP path — token refresh was fixed for direct HTTP MCP connections in Claude Code ~v2.1.59. The fix has not been ported to the
mcp-proxy.anthropic.compath.
- External IdP compounds the issue — per #82, claude.ai ignores
authorization_endpoint/token_endpointfrom OAuth metadata when an external IdP (Entra ID, Okta, Auth0 etc.) is used. This means both initial auth discovery and token refresh are broken on the proxy path for external IdP setups.
- First-party connectors unaffected — Slack, Otter etc. remain connected. Token refresh appears to work on Anthropic's internal connector infrastructure. The bug is specific to custom connectors routed through
mcp-proxy.anthropic.com.
- MCP server confirmed healthy — always-on, issuing proper offline/refresh tokens. Zero
/tokenor/authorizerequests reach the server after initial auth.
Related Issues
anthropics/claude-code#46328— same bug, Claude Code / claudeai-proxy transport (cross-post origin)- #82 — Claude.ai ignores external IdP
authorization_endpoint/token_endpoint - #155 — OAuth completes but Bearer token never attached to MCP requests
- #188 — Custom MCP server unreachable after token expiry, failing at proxy layer
anthropics/claude-code#44945— OAuth token auto-refresh broken in long-running sessions
---
*Note: This issue was researched and drafted with the help of Claude (claude.ai)
What Should 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.
Error Messages/Logs
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 (typically ~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.
Server evidence:
- Zero
/tokenor/authorizerequests reach the server after initial auth - Server correctly returns
401withWWW-Authenticate: Bearer error="invalid_token"
on expired token — a compliant client should use this to trigger a refresh
- Server is confirmed always-on and issuing proper refresh tokens at initial auth
Note: Token refresh works correctly via Claude Code direct HTTP path (~v2.1.59).
The bug is specific to the mcp-proxy.anthropic.com proxy path used by the
Claude.ai web connector. Cross-reference: anthropics/claude-code#46328
Claude Model
Sonnet (default)
Is this a regression?
I don't know
Last Working Version
_No response_
Claude Code Version
Claude Web
Platform
Anthropic API
Operating System
macOS
Terminal/Shell
Terminal.app (macOS)
Additional Information
_No response_
This issue has 2 comments on GitHub. Read the full discussion on GitHub ↗