fix(api): enforce oidc nonce binding in authorization code flow#82
Merged
fix(api): enforce oidc nonce binding in authorization code flow#82
Conversation
There was a problem hiding this comment.
Pull request overview
This pull request implements OIDC nonce binding in the authorization code flow, enhancing security by preventing replay attacks. The nonce parameter is now persisted from the initial /authorize request through the pending authorization state and authorization code, ultimately being included in the ID token claims during token exchange. Critically, the implementation ensures that nonce values cannot be injected or overridden at the /token endpoint, maintaining the integrity of the OIDC flow.
Changes:
- Added database schema migration for
noncecolumn inpending_authandauth_codestables - Wired nonce persistence through the complete authorization code flow (authorize → authorize/finalize → token)
- Refactored ID token claim generation into a reusable
buildUserIdTokenClaimshelper function - Added comprehensive test coverage including unit tests, model tests, and end-to-end security validation
Reviewed changes
Copilot reviewed 11 out of 11 changed files in this pull request and generated no comments.
Show a summary per file
| File | Description |
|---|---|
| packages/api/drizzle/0008_oidc_nonce_binding.sql | SQL migration adding nonce columns to pending_auth and auth_codes tables |
| packages/api/drizzle/meta/_journal.json | Migration journal entry for the nonce binding migration |
| packages/api/src/db/schema.ts | Schema definitions for nonce columns in both tables |
| packages/api/src/models/authorize.ts | Updated createPendingAuth to accept and persist nonce parameter |
| packages/api/src/models/authCodes.ts | Updated createAuthCode to accept and persist nonce parameter |
| packages/api/src/controllers/user/authorize.ts | Capture nonce from authorization request and pass to pending auth |
| packages/api/src/controllers/user/authorizeFinalize.ts | Propagate nonce from pending auth to authorization code |
| packages/api/src/controllers/user/token.ts | Refactored ID token generation and include stored nonce in claims |
| packages/api/src/models/noncePersistence.test.ts | Unit tests verifying nonce persistence in both models |
| packages/api/src/controllers/token.test.ts | Unit tests for nonce handling in token schema and ID token claims |
| packages/test-suite/tests/api/oidc-nonce-code-flow.spec.ts | End-to-end test validating complete nonce flow and security properties |
💡 Add Copilot custom instructions for smarter, more guided reviews. Learn how to get started.
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
Summary
noncefrom/authorizeintopending_authandauth_codesnonceclaim in userid_tokenduring authorization code exchange/tokenstandards-compliant by sourcing nonce from stored authorization state (not token request input)/authorize->/authorize/finalize->/tokennonce behaviorChanges
pending_auth.nonceandauth_codes.noncetests/api/oidc-nonce-code-flow.spec.tsValidation
npm run tidynpm run buildnpm run test -w @DarkAuth/api -- src/controllers/token.test.ts src/models/noncePersistence.test.tscd packages/test-suite && PW_REPORTER=dot PW_ARTIFACTS=off npx playwright test tests/api/oidc-nonce-code-flow.spec.ts --reporter=dot