Severity by source
CVSS:4.0/AV:N/AC:H/AT:P/PR:N/UI:P/VC:N/VI:H/VA:N/SC:N/SI:N/SA:N/E:X/CR:X/IR:X/AR:X/MAV:X/MAC:X/MAT:X/MPR:X/MUI:X/MVC:X/MVI:X/MVA:X/MSC:X/MSI:X/MSA:X/S:X/AU:X/R:X/V:X/RE:X/U:X
Network-delivered OAuth callback attack requiring non-default cookie config, user interaction to complete forged callback, and no confidentiality impact - only high integrity loss via session or account hijack.
Primary rating from Vendor (VulnCheck).
CVSS VectorVendor: VulnCheck
Lifecycle Timeline
3Blast Radius
ecosystem impact- 12 npm packages depend on better-auth (4 direct, 8 indirect)
Ecosystem-wide dependent count for version 1.6.2.
DescriptionCVE.org
better-auth versions before 1.6.2 fail to validate the OAuth state parameter against the stored nonce when using cookie-backed state storage without PKCE. Attackers can forge the state parameter and supply an attacker-controlled authorization code to create authenticated sessions bound to the attacker's external identity or persistently link attacker accounts to victim profiles.
AnalysisAI
OAuth state validation bypass in better-auth before 1.6.2 enables network-based attackers to forge the OAuth callback state parameter and supply attacker-controlled authorization codes, creating authenticated sessions in the victim's browser that are cryptographically bound to the attacker's external identity. Account-linking flows are equally exposed, permitting the attacker's provider account to be persistently linked to an authenticated victim row in the application's user store. Exploitation is constrained to a specific non-default configuration (cookie-backed state storage with PKCE disabled), and no public exploit has been identified at time of analysis.
Technical ContextAI
better-auth is an npm authentication library (CPE: cpe:2.3:a:better-auth:better-auth:*:*:*:*:*:*:*:*) that implements OAuth 2.0 social login, generic OAuth, OIDC SSO, and SAML relay flows. The defect (CWE-287: Improper Authentication) lives in parseGenericState, the shared primitive that validates the OAuth state parameter returned by identity providers at the authorization callback. The cookie-backed branch of that function decrypted the oauth_state cookie and verified its expiry but never compared the incoming state query parameter to the nonce that generateGenericState had embedded in the cookie at sign-in initiation. The database-backed path (the library default) was immune because its verification row is keyed by state value, making equality enforcement implicit in the lookup itself. The vulnerable code path affects every flow that passes through parseGenericState with cookie storage active: generic-oauth, social providers, account-link, oauth-proxy passthrough, OIDC SSO, and SAML relay state. The fix (PR #8949, commit 9deb7936a) writes oauthState: state into the encrypted cookie payload at generation time and rejects callbacks where parsedData.oauthState !== state.
RemediationAI
The primary remediation is to upgrade to better-auth 1.6.2 or later (current stable: 1.6.10) via npm install better-auth@latest; the patch was merged in PR #8949 (commit 9deb7936a) on 2026-04-09 and is confirmed fixed per the vendor advisory at https://github.com/better-auth/better-auth/security/advisories/GHSA-wxw3-q3m9-c3jr. For deployments that cannot immediately upgrade, the vendor documents two effective workarounds: first, switch betterAuth({ account: { storeStateStrategy } }) from 'cookie' back to the default value 'database', which is not affected because its state lookup is keyed by the state value itself - this requires the application's database to handle state table writes and may affect deployments in stateless or cookie-only environments; second, enable PKCE (pkce: true) on all OAuth providers configured via genericOAuth, which prevents an attacker-supplied code from completing the token exchange without the corresponding code verifier - this requires that all upstream providers support PKCE, which should be verified before enabling. Applying either workaround eliminates the attack path without a version upgrade, but upgrading remains the authoritative fix.
More in Better Auth
View allBetter Auth is an authentication library for TypeScript. Rated high severity (CVSS 7.9), this vulnerability is remotely
Authorization bypass in the @better-auth/oauth-provider plugin for Better Auth (versions >= 1.4.8-beta.7 and < 1.6.5, pl
Privilege-escalating account takeover in the @better-auth/scim plugin (versions 1.4.0-beta.27 through 1.6.21 and 1.7.0-b
Authentication bypass in Better Auth before 1.6.11 stems from insecure cryptographic defaults in the legacy oidcProvider
Denial of service in Better Auth (npm) before 1.4.2 lets an unauthenticated remote attacker poison the router's base pat
Path normalization bypass in Better Auth before v1.4.5 allows unauthenticated remote attackers to circumvent `disabledPa
Authorization bypass in @better-auth/scim versions 1.5.0 through 1.7.0-beta.3 allows any authenticated user to fully tak
Pre-account hijacking in better-auth (npm) allows a remote attacker to gain persistent, password-based access to any vic
Multiple authentication bypass vulnerabilities in @better-auth/sso before version 1.6.21 enable low-privileged attackers
Two domain-ownership authentication bypass flaws in @better-auth/sso allow authenticated organization owners to compromi
Two-factor authentication bypass in better-auth (npm) before version 1.4.9 allows network-accessible attackers holding v
Privilege escalation in Better Auth SSO plugin (1.2.10 to <1.6.11) allows any authenticated organization member to regis
Same weakness CWE-287 – Improper Authentication
View allSame technique Authentication Bypass
View allShare
External POC / Exploit Code
Leaving vuln.today
EUVD-2026-51852
GHSA-4hp3-gxv8-7g37