Skip to main content

MCPX_OAUTH_CALLBACK_MISMATCH

Severity: error Domain: OAuth

What happened​

mcpproxy received an OAuth redirect, but the redirect_uri parameter in the authorisation response differs from the one mcpproxy persisted for this server. Returning a token in this state would violate RFC 8252 / PKCE binding, so the flow is aborted.

Common causes​

  • The OAuth client registered with the provider lists a different redirect URI than the one mcpproxy uses.
  • The provider was reconfigured between the start of the login and the callback (rare).
  • mcpproxy's persisted port changed because the saved port was already in use.
  • A reverse proxy in front of mcpproxy rewrote the redirect_uri.

How to fix​

Update the provider configuration​

mcpproxy uses http://127.0.0.1:<port>/oauth/callback (with a per-server persisted port). Add that exact URI to your OAuth client's allowed redirect URIs in the provider's developer console.

For most providers wildcards aren't allowed; you'll need to register the exact port. When oauth.redirect_uri is not set, mcpproxy allocates a loopback port on the first login and persists it, reusing it on subsequent logins — so the callback URL is usually stable, but it is not guaranteed if that port is taken later.

Pin the redirect URI​

If the provider requires an exact callback URL, pin it with oauth.redirect_uri:

{
"name": "my-server",
"oauth": {
"client_id": "...",
"redirect_uri": "http://127.0.0.1:53412/oauth/callback"
}
}

mcpproxy binds that exact port and path and sends that exact string to the provider. The value must be an RFC 8252 loopback redirect: http scheme, a loopback host, and an explicit port; the path can be anything the provider requires — mcpproxy's callback listener serves whatever path the pin specifies (a pin with no path at all binds /, not /oauth/callback — that remains the default only when redirect_uri is omitted entirely). A malformed value, or a pinned port already in use, fails the login with an explicit error naming redirect_uri rather than falling back to a random port.

Then re-register that exact URI on the provider side.

If a reverse proxy is in front​

Make the proxy preserve the original redirect_uri query parameter and avoid host rewriting on /oauth/callback. mcpproxy ships a self-hosted callback — it doesn't need to be exposed publicly, only locally.