codex mcp login ignores WWW-Authenticate resource_metadata during DCR discovery
Nobody has claimed this yet.
- Dominant language
- Rust
- Stars
- 125k
- Forks
- 19.4k
- PR merge metrics
- PR metrics pending
Description
Summary
codex mcp login <server> --oauth-client-registration dcr does not follow the absolute resource_metadata URL advertised in the MCP server's 401 WWW-Authenticate challenge. Instead, it probes only .well-known metadata paths on the MCP resource origin. When those paths return 404, Codex falls back to dynamic registration on the MCP origin (/register) rather than discovering the distinct authorization server and its advertised registration_endpoint.
This breaks deployments where:
- the MCP resource server and OAuth authorization server are different origins;
- the resource server advertises protected-resource metadata through an absolute, centralized URL in
WWW-Authenticate; and - the MCP resource origin intentionally does not serve
.well-known/oauth-protected-resourceitself.
Other MCP clients that follow the challenge's resource_metadata URL complete the flow.
Environment
- Codex CLI 0.152.1 (
rust-v0.152.1) - macOS arm64
codex mcp login oauth-repro --oauth-client-registration dcr
Minimal repro
The self-contained executable reproducer is in the first comment below. Save it as codex_mcp_oauth_dcr_repro.py and run:
python3 codex_mcp_oauth_dcr_repro.py
It starts three loopback-only servers:
- MCP resource server:
/mcpreturns401with an absoluteresource_metadataURL. - Central protected-resource-metadata server: returns an
authorization_serversvalue pointing at server 3. - OAuth authorization server: advertises
/oauth2/registeras itsregistration_endpoint.
The authorization server's DCR handler deliberately returns:
{"probe":"advertised-registration-endpoint"}
so a request reaching it is unambiguous and does not begin a browser OAuth flow.
Actual result from 0.152.1:
Error: Registration failed: Dynamic registration failed: Registration failed:
HTTP 404 Not Found: {"probe":"resource-not-found"}
The mock request log contains no request to the centralized PRM server and no request to the authorization server. It shows only requests to the MCP resource origin, followed by:
POST /register
Expected behavior
Codex should follow the absolute resource_metadata URL from the WWW-Authenticate challenge, fetch its authorization_servers metadata, then post the DCR request to the full registration_endpoint advertised by that authorization server.
Why this appears inconsistent with the current code
codex-rs/rmcp-client/src/oauth_client_registration.rs constructs an AuthorizationManager and calls resolve_metadata(). The same release's oauth_client_registration_tests.rs includes verified_issuer_can_delegate_authorization_and_token_to_one_origin, which verifies a DCR POST is sent to a delegated authorization-server endpoint.
The reproducer suggests the direct mcp login discovery path does not preserve or use the initial WWW-Authenticate challenge's resource_metadata URL when resolving metadata. That occurs before the delegated-registration test coverage.
Related issues
- #34684: macOS Codex OAuth discovery failure while other MCP clients work on the same machine.
- #20503: DCR interoperability issue involving registration metadata.
Contributor guide
First steps
- Read the whole issue, then the project's contributing guide.
- Comment on the issue to say you are picking it up — it saves two people doing the same work.
- Fork the repository and make your change on a branch.
- Open a pull request that references the issue number.
Research direction
Start in codex-rs/rmcp-client/src/oauth_client_registration.rs, then read oauth_client_registration_tests.rs, especially verified_issuer_can_delegate_authorization_and_token_to_one_origin. Run the linked codex_mcp_oauth_dcr_repro.py reproducer and inspect discovery requests. Done means the absolute resource_metadata URL is followed and DCR reaches the advertised registration_endpoint.
Written by the indexing model from the issue text.
Assessment
- Tech stack
- rust
- Domain
- api, authentication
- Issue type
- Bug
- Difficulty
- 3/5
- Estimated time
- 1-2 days
- Activity status
- Active
- Clarity
- Mostly clear
- Newbie friendliness
- 68/100