OAuth 2.0
Reconnaissance & Discovery
-
Identify the Grant Type: Determine if the application uses Authorization Code, Implicit (legacy), Client Credentials, or Resource Owner Password Credentials.
-
Map Endpoints: Locate the Authorization Endpoint (
/authorize), Token Endpoint (/token), and UserInfo Endpoint (/userinfo). -
Analyze Client Parameters: Identify the
client_idand check ifclient_secretis visible in client-side code (mobile/SPA). -
Review Discovery Document: Check
/.well-known/openid-configurationor/.well-known/oauth-authorization-serverfor supported scopes, claims, and endpoints.
Authorization Request Manipulation (/authorize)
-
Test
redirect_uriValidation (Exact Match): Modify theredirect_urito a domain you control. -
Test
redirect_uriTraversal: Attempt path traversal (e.g.,https://site.com/callback/../../attacker.com). -
Test
redirect_uriFuzzy Matching: Check if subdomains or related domains are accepted (e.g.,https://attacker.site.comorhttps://site.com.attacker.com). -
Check for Open Redirects: Use an open redirect on the trusted domain in the
redirect_uriparameter (e.g.,https://site.com/logout?next=https://attacker.com). -
Test for CSRF (Missing
state): Remove thestateparameter and replay the flow. -
Test for CSRF (Static
state): Verify if thestateparameter is random and unique per session. -
Scope Escalation: Manually add privileged scopes (e.g.,
admin,write,all) to the authorization request.
Testing redirect_uri
Baseline Validation
-
Identify the Allowed URI: Capture a legitimate authorization request and note the exact
redirect_urivalue. -
Verify Exact Match Enforcement: Change a single character in the path or subdomain to see if the server rejects it (e.g., change
/callbackto/callbac). -
Check HTTP vs. HTTPS: Change the protocol to
http://to see if the server allows downgrades (unlesslocalhostis used).
Domain & Logic Bypasses
-
Test Subdomain Wildcards: Attempt to use a different subdomain on the trusted domain (e.g.,
api.target.cominstead ofapp.target.com). -
Test "Ends With" Logic: Register a domain that ends with the target's name (e.g.,
target.com.attacker.com) and test it. -
Test "Contains" Logic: Create a directory structure that mimics the target domain (e.g.,
attacker.com/target.com/callback). -
Test IPv6/IP Decimal: Replace the domain name with its IP address, decimal IP representation, or IPv6 literal
[::1].
Syntactic Manipulation & Encoding
-
The "@" Bypass (Authority Confusion): Inject
target.com@attacker.comto treat the target domain as a username credential for the attacker's site. -
Double URL Encoding: Encode characters like
.(%252E) and/(%252F) to bypass filters that decode only once. -
Null Byte Injection: Append
%00to the end of a valid domain followed by your payload (e.g.,target.com%00.attacker.com). -
Whitespace Injection: Append tabs (
%09), newlines (%0a), or spaces (%20) to the URI. -
Backslash Conversion: Replace forward slashes
/with backslashes\(common bypass for Windows-based servers).
Parameter Pollution & Chaining
-
Parameter Pollution (HPP): Add a second
redirect_uriparameter (e.g.,?redirect_uri=VALID&redirect_uri=ATTACKER). -
Chained Open Redirect: Identify an open redirect vulnerability on the trusted domain (e.g.,
target.com/logout?next=...) and use it as theredirect_urivalue. -
Fragment Injection: Append
#to truncate the path if the server validation is loose (e.g.,target.com#attacker.com).
Token Exchange & Handling (/token)
-
Authorization Code Replay: Attempt to exchange the same Authorization Code for an access token more than once.
-
PKCE Downgrade: If PKCE is used, remove the
code_challengeandcode_challenge_methodfrom the authorization request. -
PKCE Method S256 vs plain: Force the method to
plainif the server supports it, to bypass hashing requirements. -
Client Secret Leakage: Check if the
client_secretis leaked in JS files, GitHub repos, or mobile app binaries. -
Token Injection via Implicit Flow: If the app supports
response_type=token, try to force this flow even if the app defaults tocode. -
Referer Header Leakage: Check if the Authorization Code or Access Token leaks in the
Refererheader when linking to external sites.
Token Validation & Session Management
-
JWT Analysis (Algorithm Confusion): If the token is a JWT, test changing the algorithm from
RS256toHS256(HMAC) using the public key as the secret. -
JWT "None" Algorithm: Change the algorithm header to
noneand remove the signature. -
Token Expiration: Verify that Access Tokens expire within a reasonable timeframe (e.g., 1 hour).
-
Refresh Token Rotation: Ensure that using a Refresh Token invalidates the previous one (if rotation is enabled) or that they are securely bound.
-
Session Fixation: Check if the user's session ID changes after a successful OAuth login.
-
IDOR on UserInfo: Use an Access Token from User A to request
/userinfodata for User B (if the endpoint accepts a user identifier).
Account Takeover (Pre-Authentication)
-
Pre-Auth Account Takeover: Create an account with an email address (e.g.,
victim@company.com) manually, then sign in with OAuth using the same email. Check if the accounts merge without verification. -
Duplicate Email Registration: Register a manual account with the same email after an OAuth account exists to see if it overwrites the OAuth link.
The PKCE Downgrade Attack
Proof Key for Code Exchange (PKCE) protects public clients (like mobile apps) that cannot safely store a client secret. It works by hashing a secret code_verifier into a code_challenge.
-
The Vulnerability: Many servers support PKCE but do not enforce it for all clients.
-
The Attack: An attacker intercepts the initial
/authorizerequest and strips out thecode_challenge. If the server is not configured to mandate PKCE, it will fall back to the standard flow. The attacker can then use the intercepted Authorization Code to get a token without needing thecode_verifier.