anthropics / anthropics/claude-ai-mcp
Unauthenticated MCP server forced through OAuth: claude.ai uses the origin's /.well-known/oauth-authorization-server when the resource has no protected-resource metadata
- Lingua principale
- Nessun dato sulla lingua
- Stelle
- 471
- Fork
- 76
- Metriche di merge delle PR
- Nessuna PR unita negli ultimi 30g
Descrizione
### MCP server URL
`https:///mcp/` (self-hosted n8n; reproduces on any instance)
### Where does the issue occur?
Connect button
### Transport used
streamable-http
### Client registration type
My server does not have auth
### SSE only: Does your server return the expected status code for POST requests?
Not applicable (my server does not use SSE)
### When did you last reproduce this?
2026-08-26 9:43AM CET
### Browser and OS
macOS 26.5 Chrome 151
### Describe the issue
An MCP endpoint that requires no authentication is still forced through OAuth. An unauthenticated `initialize` returns 200, the endpoint sends no `WWW-Authenticate`, and it publishes no RFC 9728 protected-resource metadata. claude.ai nonetheless shows a Connect button and redirects to the host's OAuth sign-in / consent screen.
The only OAuth signal anywhere on that origin is `/.well-known/oauth-authorization-server`, which returns 200. It is there for *other* resources on the same origin: n8n hosts one authorization server at the instance root, and separate workflow triggers on that origin can opt into n8n user auth. Individual MCP endpoints on the same origin can be unauthenticated.
So it looks like claude.ai falls back to probing the authorization-server document at the MCP server's *origin* when the *resource* has no protected-resource metadata, and treats finding one as "this resource requires OAuth".
I've left the server URL above as a placeholder, this reproduces on any n8n instance, self-hosted or Cloud, that exposes an MCP Server Trigger with `Authentication: None`.
### Issue details
```shell
POST /mcp/ (initialize, no Authorization header)
-> 200, content-type: text/event-stream, valid MCP initialize result
-> no WWW-Authenticate header
GET /.well-known/oauth-protected-resource/mcp/ -> 404 (application/json)
GET /.well-known/oauth-protected-resource -> 404 (application/json)
GET /.well-known/oauth-authorization-server/mcp/ -> 404
GET /.well-known/openid-configuration -> 404
GET /.well-known/oauth-authorization-server -> 200 (application/json)
Observed result: the connector shows "Connect", which redirects to the instance
sign-in page with a return path of /oauth/consent, so the flow already
reached /authorize on the origin's authorization server.
```
### Expected behavior
Discovery should abort here rather than start an OAuth flow:
- "MCP clients MUST use OAuth 2.0 Protected Resource Metadata for authorization server discovery."
- Authorization-server metadata URLs are built from the issuer identifier taken from the protected-resource metadata document ("Validate RS metadata, build AS metadata URL"), not from the MCP server's own URL.
- The no-metadata branch of the discovery flow ends in "Abort or use pre-configured values" after `GET /.well-known/oauth-protected-resource` misses.
- The flow is entered from `HTTP 401 Unauthorized`, and authorization is OPTIONAL for MCP implementations. This server returns 200 and never challenges.
Expected: the connector connects unauthenticated and lists tools, with no sign-in prompt.
### Logs from your server
```shell
```
### Additional context
_No response_
Guida per i contributori
Nessuna guida per i contributori indicizzata per questo repository
Valutazione
Questa issue non è ancora stata valutata.