Overview
DPoP (Demonstrating Proof-of-Possession) is an OAuth 2.0 extension that enhances security by binding access tokens to a client’s private key. This prevents token theft and replay attacks by requiring cryptographic proof that the client possessing the token also possesses the private key used to request it.What is DPoP?
DPoP provides application-level proof-of-possession security for OAuth 2.0 with the following benefits:- Token Binding: Access tokens are cryptographically bound to the client’s key pair
- Theft Protection: Stolen tokens cannot be used without the corresponding private key
- Replay Attack Prevention: Each request includes a unique proof-of-possession signature
- Enhanced Security: Complements OAuth 2.0 with additional cryptographic guarantees
DPoP uses ES256 (ECDSA with P-256 and SHA-256) key pairs for cryptographic operations.
Basic Setup
Choose one of three setup methods based on your deployment strategy:Option 1: Environment Variables (Recommended for Production)
For production deployments with pre-generated keys:1
Generate DPoP key pair
Use the SDK to generate keys:
2
Add keys to environment variables
Store the generated keys in your
.env.local file:.env.local
3
Enable DPoP in Auth0Client
Configure your Auth0 client to use DPoP:
lib/auth0.ts
Option 2: Dynamic Key Generation
For dynamic key generation during application startup:lib/auth0.ts
Option 3: Programmatic Configuration
For advanced configurations with custom options:lib/auth0.ts
Making DPoP-Protected Requests
The recommended approach is to use thecreateFetcher method, which handles all DPoP complexity automatically.
DPoP Inheritance Behavior
Fetchers created withcreateFetcher automatically inherit the global DPoP configuration from your Auth0Client instance:
This inheritance pattern aligns with auth0-spa-js behavior, providing consistent developer experience across Auth0 SDKs.
Using the Fetcher
App Router (Server Components and Route Handlers)
app/api/data/route.ts
Pages Router (API Routes)
pages/api/data.ts
Per-Fetcher Override
You can override the global DPoP setting for specific fetchers:Configuration Options
Fine-tune DPoP behavior for your environment and security requirements.Clock Tolerance and Skew
Configure timing validation to handle clock differences between client and server:lib/auth0.ts
Environment Variable Configuration
Configure DPoP settings through environment variables:.env.local
Error Handling
Handle DPoP-specific errors gracefully with proper error detection.Handling DPoP Errors
app/api/data/route.ts
Automatic Nonce Error Retry
The SDK automatically handles DPoP nonce errors with intelligent retry logic:Advanced Usage
Custom Access Token Factory
Override the default token retrieval with custom logic:Custom Access Token Scopes
Pass token options directly to individual requests:Conditional DPoP Usage
Enable DPoP selectively based on environment or security requirements:Custom Fetch Implementation
Add logging, metrics, or custom headers while preserving DPoP functionality:Token Audience Validation
When using DPoP with multiple audiences (e.g., via MRRT policies), ensure each access token is sent only to its intended API.How Mismatches Happen
fetcher1 to call endpoints that should use fetcher2. The API will reject with:
Mitigation Strategies
-
Scope fetcher instances appropriately
- Create one fetcher per API/audience combination
- Use clear, descriptive variable names
- Consider namespacing or module organization
-
Configure MRRT policies correctly
- Ensure policies include all required audiences
- Set
skip_consent_for_verifiable_first_party_clients: true - Only include custom scopes (OIDC scopes are automatic)
-
Validate in development
- Log the
audclaim from decoded tokens - Implement clear error handling for audience mismatches
- Test each fetcher against its intended API
- Log the
-
API server validation
- Validate the
audclaim matches expected audience - Use consistent audience strings
- Validate the
Example: Proper Token Routing
Security Best Practices
Follow these guidelines for secure DPoP implementation:- Key Management: Use hardware security modules (HSMs) for key storage in production
- Key Rotation: Implement regular key rotation policies for long-lived applications
- Monitoring: Monitor DPoP error rates to detect potential attacks or configuration issues
- Clock Tolerance: Keep clock tolerance as low as possible (≤ 30 seconds recommended)
- Environment Isolation: Use unique key pairs per environment (dev, staging, production)
- Key Security: Never commit DPoP keys to version control or logs