OAuth

PKCE โ€” Proof Key for Code Exchange

Last updated: April 2026

PKCE (pronounced "pixie") is an OAuth 2.0 extension that helps protect against authorization code interception attacks. It is required for public clients (SPAs and mobile apps) and recommended for all OAuth flows in OAuth 2.1.

How PKCE works

# 1. App generates a random code_verifier
code_verifier = base64url(random(32 bytes))
# Example: dBjftJeZ4CVP-mB92K27uhbUJU1p1r_wW1gFWFOEjXk

# 2. App creates code_challenge from verifier
code_challenge = base64url(sha256(code_verifier))
# Example: E9Melhoa2OwvFrEMTJguCHaoeK1t8URWbuGJSstw-cM

# 3. App sends code_challenge to authorization endpoint
GET /authorize
  ?code_challenge=E9Melhoa2OwvFrEMTJguCHaoeK1t8URWbuGJSstw-cM
  &code_challenge_method=S256
  &...

# 4. Server stores code_challenge with the auth code

# 5. App sends code_verifier when exchanging code for token
POST /token
  code=AUTH_CODE
  &code_verifier=dBjftJeZ4CVP-mB92K27uhbUJU1p1r_wW1gFWFOEjXk
  &...

# 6. Server verifies: sha256(code_verifier) == stored code_challenge

Enable PKCE in common providers

Auth0: Application Settings โ†’ Grant Types โ†’ enable Authorization Code (PKCE). Use auth0-react or auth0-spa-js SDK.

Okta: Application โ†’ Sign-On Policy โ†’ enable PKCE. Set pkce: true in OktaAuth config.

Cognito: App client โ†’ Auth flows โ†’ enable PKCE. Set in Amplify config.

JavaScript implementation

async function generatePKCE() {
  const verifier = crypto.getRandomValues(new Uint8Array(32));
  const challenge = await crypto.subtle.digest('SHA-256', verifier);
  return {
    code_verifier: btoa(String.fromCharCode(...verifier))
      .replace(/\+/g, '-').replace(/\//g, '_').replace(/=/g, ''),
    code_challenge: btoa(String.fromCharCode(...new Uint8Array(challenge)))
      .replace(/\+/g, '-').replace(/\//g, '_').replace(/=/g, ''),
  };
}
📚 HttpFixer Glossary โ€” all terms โ†’