Listen to this Post
CVE-2026-104850 is a high-severity authentication flaw in the official Model Context Protocol (MCP) TypeScript SDK. The vulnerability exists because the SDK’s OAuth client implementation does not bind stored OAuth credentials to the authorization server that issued them. In standard OAuth flows, a client should only present credentials—such as a `refresh_token` or client_secret—to the exact authorization server that originally issued them. However, in affected versions, the SDK allows an MCP server to dictate which authorization server receives the client’s credentials via its protected resource metadata. A malicious or compromised MCP server can therefore supply its own authorization server URL. Without any user interaction, the SDK will automatically send the previously stored `refresh_token` and `client_secret` (in 1.x) or the configured `client_secret` or signed assertion of a bundled non-interactive provider (in 1.x and 2.x) to that attacker-controlled endpoint. This effectively bypasses OAuth security boundaries and allows an attacker to harvest long-lived credentials. The flaw affects applications that use the SDK as an MCP client over HTTP with an authProvider, including custom `OAuthClientProvider` implementations and bundled providers such as ClientCredentialsProvider, PrivateKeyJwtProvider, StaticPrivateKeyJwtProvider, and (in 2.x) CrossAppAccessProvider. The vulnerability is classified as CWE-345 (Insufficient Verification of Data Authenticity) and CWE-522 (Insufficiently Protected Credentials). The patched versions are `@modelcontextprotocol/sdk` 1.31.0 for the 1.x line and `@modelcontextprotocol/client` 2.2.0 for the 2.x line. Upgrading alone is not always sufficient; developers must also set `expectedIssuer` for bundled providers and ensure that persisted credentials include an `issuer` field. If an affected client may have connected to an untrusted server, the client secret or signing key should be rotated and all tokens revoked.
DailyCVE Form:
Platform: MCP TypeScript SDK
Version: 1.12.0–1.30.1
Vulnerability: OAuth Credential Leakage
Severity: High
date: 2026-10-06
Prediction: 2026-10-06
What Undercode Say:
Bash commands and code examples related to the blog .
Check current version of the SDK npm list @modelcontextprotocol/sdk npm list @modelcontextprotocol/client Upgrade to the patched version (1.x) npm install @modelcontextprotocol/[email protected] Upgrade to the patched version (2.x) npm install @modelcontextprotocol/[email protected] npm install @modelcontextprotocol/[email protected]
// Example: Setting expectedIssuer on a bundled provider (ClientCredentialsProvider)
import { ClientCredentialsProvider } from '@modelcontextprotocol/sdk';
const provider = new ClientCredentialsProvider({
clientId: 'your-client-id',
clientSecret: 'your-client-secret',
expectedIssuer: 'https://auth.example.com' // REQUIRED after upgrade
});
// Example: Custom OAuthClientProvider – persisting issuer
class MyOAuthClientProvider implements OAuthClientProvider {
async saveTokens(tokens: OAuthTokens) {
// tokens now include issuer
await store.set('tokens', tokens);
}
async saveClientInformation(info: OAuthClientInformation) {
// info now includes issuer
await store.set('clientInfo', info);
}
async clientInformation(): Promise<OAuthClientInformation> {
return await store.get('clientInfo'); // must contain issuer
}
}
Exploit: (Educational Purposes!)
An attacker operates a malicious MCP server. The server responds to the client’s metadata discovery request with a protected resource metadata document that points to an authorization server controlled by the attacker (e.g., https://evil.example.com`). Because the vulnerable SDK does not verify that the authorization server matches the issuer of the stored credentials, the client automatically sends the `refresh_token` and `client_secret` (or the configured static secret/signed assertion) to the attacker’s endpoint. The attacker can then use those credentials to impersonate the victim application against the legitimate authorization server.ClientCredentialsProvider
<h2 class="f1b-anim" style="color:#3b82f6;border-left:4px solid #3b82f6;padding-left:12px;margin:22px 0 10px 0;font-weight:bold">Protection: from this CVE</h2>
- Upgrade to `@modelcontextprotocol/sdk` 1.31.0 or later (1.x) or `@modelcontextprotocol/client` 2.2.0 or later (2.x).
- For bundled providers (,PrivateKeyJwtProvider,StaticPrivateKeyJwtProvider,CrossAppAccessProvider), explicitly passexpectedIssuer.issuer`.
- Ensure that any persisted credentials include the `issuer` field. If not, add it or clear the stored credentials so users sign in again.
- For custom `OAuthClientProvider` implementations, save exactly what `saveTokens()` and `saveClientInformation()` provide, including
– Rotate the client secret or signing key and revoke tokens if an affected client may have connected to an untrusted MCP server.
– If upgrading is not possible, connect OAuth clients only to MCP servers you fully trust.
Impact:
Successful exploitation allows an attacker to steal long-lived OAuth credentials, including refresh tokens and client secrets. These credentials can be used to impersonate the victim application, access protected resources, and potentially move laterally across any service that trusts the same identity provider. The vulnerability requires no user interaction and is automatable, making it a high-severity risk for any application using the affected SDK versions over HTTP with OAuth enabled.
🎯Let’s Practice Exploiting & Learn Patching For Free:
🎓 Live Courses & Certifications:
Join Undercode Academy for Verified Certifications
🚀 Request a Custom Project:
Secure, high-velocity infrastructure and disruptive technological engineering. Contact our engineering team for high-tier development and proprietary systems:
[email protected]
💎 Smart Architecture | 🛡️ Secure by Design | ⭐ Trusted by Thousands
Sources:
Reported By: github.com
Extra Source Hub:
Undercode

