Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Proposal/discussion: OIDC nonce claim requirement #2002

Closed
deleterepo opened this issue Jul 26, 2024 · 34 comments · Fixed by #2159
Closed

Proposal/discussion: OIDC nonce claim requirement #2002

deleterepo opened this issue Jul 26, 2024 · 34 comments · Fixed by #2159
Assignees
Labels
1) Discussion ongoing Issue is opened and assigned but no clear proposal yet V51 Group issues related to OAuth Will be closed if no response/opposite arguments _5.0 - prep This needs to be addressed to prepare 5.0

Comments

@deleterepo
Copy link

As per the discussion in #1969, the nonce claim is a specific OIDC claim to bind an ID token to a client, to mitigate replay attacks. See here: https://openid.net/specs/openid-connect-core-1_0.html#IDToken

We can have a requirement such as this:

Verify that the nonce parameter sent in the authorization request is included in the nonce claim of the issued ID token, and that the client ensures that the nonce claim value is equal to the original value sent in the authorization request.

@elarlang

@elarlang elarlang added the V51 Group issues related to OAuth label Jul 26, 2024
@tghosth tghosth added 1) Discussion ongoing Issue is opened and assigned but no clear proposal yet _5.0 - prep This needs to be addressed to prepare 5.0 labels Jul 29, 2024
@elarlang
Copy link
Collaborator

We also have requirement

# Description L1 L2 L3
51.2.2 [ADDED] Verify that the Client is using the PKCE flow or alternatively the OpenID Connect "nonce" parameter and the respective Claim in the ID Token.

I prefer the requirement to say clearly, what security problem it solves. E g for be sure that the ID-token is sent to the same client that started the auth* process, check the nonce parameter before accepting the token.

@elarlang
Copy link
Collaborator

Well, some input for feedback and wordsmithing. Terminology and grammar needs validation as well:

Verify that the OAuth Client mitigates the replay attack by validating the nonce claim in the ID-token to be the same value as it was sent via nonce parameter in the authentication request to the authorization server.

ping @deleterepo @randomstuff @TobiasAhnoff

@jmanico
Copy link
Member

jmanico commented Sep 11, 2024 via email

@elarlang elarlang added the 4) proposal for review Issue contains clear proposal for add/change something label Sep 15, 2024
@elarlang
Copy link
Collaborator

elarlang commented Sep 15, 2024

So the proposal is delete current 51.2.2 and add new requirement to OIDC Client section (not made yet):

Verify that the OAuth client mitigates replay attacks by ensuring that the nonce claim in the ID token matches the nonce value sent in the authentication request to the authorization server.

Should be in the requirement also OIDC client?

ping @randomstuff @TobiasAhnoff

@TobiasAhnoff
Copy link

TobiasAhnoff commented Sep 16, 2024

A thing to note here is that when implementing the code flow according to FAPI2 there seems to be no need to verify the ID token in the same way as when using other OIDC flows, see
https://openid.bitbucket.io/fapi/fapi-2_0-security-profile.html#section-5.5

A suggestion to align with that is to have

Verify that the OAuth client mitigates replay attacks by using code and PKCE with a confidential client or ensuring that the nonce claim in the ID token matches the nonce value sent in the authentication request to the authorization server.

But from reading OIDC specs, at this point, I´m not 100% sure that all 3 conditions are a requirement for skipping the nonce and signature check as FAPI2 states? So perhaps just have (as suggested in previous comments)

Verify that the OAuth client mitigates replay attacks by ensuring that the nonce claim in the ID token matches the nonce value sent in the authentication request to the authorization server.

@randomstuff
Copy link
Contributor

randomstuff commented Sep 16, 2024

But from reading OIDC specs, at this point, I´m not 100% sure that all 3 conditions are a requirement for skipping the nonce and signature check as FAPI2 states?

@TobiasAhnoff, when receiving the ID token directly from the backend (authorization code flow), OpenID Connect allows you to skip the signature verification. This is explained in 3.1.3.7 (6) :

If the ID Token is received via direct communication between the Client and the Token Endpoint (which it is in this [the Authorization code] flow), the TLS server validation MAY be used to validate the issuer in place of checking the token signature.

As for skipping the nonce signature, this is because using PKCE is considered to already protect against replay attacks and ensure freshness.

If this is good enough for FAPI 2.0, I believe this might be good enough for ASVS (right?). (However, as the nonce parameter is required anyway there is not much benefit in not verifying it…)

@elarlang
Copy link
Collaborator

If we are not sure what is the latest-latest-latest technical solution or we are not sure how mature is the latest spec and will it be used in practice, then we should not take the risk and write it to the requirement as "hard-coded one-way to do things".

We can go with requirements like: Verify that OAuth client mitigates ID-token replay attacks. For example, by ensuring that the nonce claim in the ID token matches the nonce value sent in the authentication request to the authorization server OR /using something else/.

From the defense point of view, we should only care, that it is not possible to do the attack. How it is achieved, is not that important.

@TobiasAhnoff
Copy link

This is explained in 3.1.3.7 (6)

@randomstuff thank you, there are a lot of specs to read!

Perhaps this is enough for an ASVS verification?

Verify that OAuth client mitigates ID-token replay attacks. For example, by ensuring that the nonce claim in the ID token matches the nonce value sent in the authentication request to the authorization server.

@elarlang
Copy link
Collaborator

This simplicity works for me, everything that must be said by ASVS is said, and the rest is the responsibility for projects like testing guides or cheat sheet series.

@elarlang
Copy link
Collaborator

What should be the chapter name for this one?

@jmanico
Copy link
Member

jmanico commented Sep 20, 2024

I would suggest "OAuth Replay Attack Prevention"

@TobiasAhnoff
Copy link

Since ID Tokens are OIDC (not OAuth) a suggestion is to use terminology from the OIDC spec (see https://openid.net/specs/openid-connect-core-1_0.html#CodeIDToken), perhaps:

Verify that the Client mitigates ID Token replay attacks. For example, by ensuring that the nonce claim in the ID Token matches the nonce value sent in the Authentication Request to the OpenID Provider.

And the chapter name "OIDC ID Token Replay Attack Prevention"

Or should we keep using some OAuth terminology e g "authorization request" and "authorization server"?

@randomstuff
Copy link
Contributor

Since ID Tokens are OIDC (not OAuth) a suggestion is to use terminology from the OIDC spec

Then, it should be "Verify that the Relying Party mitigates ID token replay attacks. […]”

@TobiasAhnoff
Copy link

Yes, but maybe we should also clarify that for ID Tokens the Relying Party is the client, not the OAuth Resource Server (which sometimes also is referred as a relying party, and the OIDC spec use the term Client

if a nonce value was sent in the Authentication Request, a nonce Claim MUST be present and its value checked to verify that it is the same value as the one that was sent in the Authentication Request. The Client SHOULD check the nonce value for replay attacks. The precise method for detecting replay attacks is Client specific.

@randomstuff Maybe this better captures the OIDC terminology?
(without the risk of confusing resource servers as the relying party)

Verify that the Client (as the Relying Party) mitigates ID Token replay attacks. For example, by ensuring that the nonce claim in the ID Token matches the nonce value sent in the Authentication Request to the OpenID Provider.

@elarlang
Copy link
Collaborator

Let's go with that, propose section name for that as well.

@randomstuff
Copy link
Contributor

@TobiasAhnoff, yes you are right OpenID Connect uses the term "client" throughout so maybe there was no need to ass the "relying party" wording in there after all.

@elarlang
Copy link
Collaborator

Asking feedback for the idea (the last sentence in brackets)

Verify that the Client (as the Relying Party) mitigates ID Token replay attacks. For example, by ensuring that the nonce claim in the ID Token matches the nonce value sent in the Authentication Request to the OpenID Provider (that was sent in the authorization request to the OAuth Authorization Server).

Chapter "OIDC Client"?

@TobiasAhnoff
Copy link

TobiasAhnoff commented Sep 26, 2024

I think the chapter/section heading should be "OIDC Client", but I´m not sure on the "bracket sentence"....

One argument is that is should not be needed, the reader should understand how OIDC and OAuth terminology overlaps.
On the other hand it could be good to clarify that the "Authentication Request to the OpenID Provider" and "authorization request to the OAuth Authorization Server" is the same request...(even if ID Tokens is not part of OAuth)

I´m not sure if this is better but an alternative is to have:

Verify that the Client (as the Relying Party) mitigates ID Token replay attacks. For example, by ensuring that the nonce claim in the ID Token matches the nonce value sent in the Authentication Request to the OpenID Provider (in OAuth2 refereed to as the Authorization request sent to the Authorization Server).

Perhaps this will be easier to decide when we see the full OAuth/OIDC chapter?

@elarlang elarlang added the 5) awaiting PR A proposal hs been accepted and reviewed and we are now waiting for a PR label Sep 26, 2024
elarlang pushed a commit to elarlang/ASVS that referenced this issue Sep 27, 2024
@elarlang elarlang reopened this Oct 16, 2024
@elarlang elarlang added 4) proposal for review Issue contains clear proposal for add/change something 5) awaiting PR A proposal hs been accepted and reviewed and we are now waiting for a PR and removed 6) PR awaiting review labels Oct 16, 2024
elarlang pushed a commit to elarlang/ASVS that referenced this issue Oct 17, 2024
@elarlang elarlang added 6) PR awaiting review and removed 4) proposal for review Issue contains clear proposal for add/change something 5) awaiting PR A proposal hs been accepted and reviewed and we are now waiting for a PR labels Oct 17, 2024
@elarlang elarlang linked a pull request Oct 17, 2024 that will close this issue
elarlang pushed a commit that referenced this issue Oct 17, 2024
@randomstuff
Copy link
Contributor

We have:

[ADDED] Verify that the Client is using the PKCE flow or alternatively the OpenID Connect "nonce" parameter and the respective Claim in the ID Token.

The current FAPI 2.0 draft have:

nonce/signature check can be skipped by clients, PKCE cannot (security improvement)

Should we align with this and require the usage of PKCE at least for L3 (even if nonce is used)?

@elarlang
Copy link
Collaborator

Just in case saying, that the referenced requirement was proposed to be deleted and now is deleted.

@TobiasAhnoff
Copy link

Should we align with this and require the usage of PKCE at least for L3 (even if nonce is used)?

Yes, I think so, maybe 51.51. should be a mix with the deleted 51.3.2?
(there are other ASVS requirements mandating PKCE when code is used)

Verify that the Client (as the Relying Party) mitigates ID Token replay attacks by using PKCE or alternatively (when code is not used) by ensuring that the nonce claim in the ID Token matches the nonce value sent in the Authentication Request to the OpenID Provider (in OAuth2 refereed to as the Authorization request sent to the Authorization Server).

@elarlang elarlang reopened this Oct 20, 2024
@jmanico
Copy link
Member

jmanico commented Oct 20, 2024 via email

@randomstuff
Copy link
Contributor

randomstuff commented Oct 20, 2024

@jmanico, Actually usage of PKCE is mostly required by the OAuth 2.1 draft so I think it would make sense to require it in L1:

To prevent injection of authorization codes into the client, using code_challenge and code_verifier is REQUIRED for clients

@jmanico
Copy link
Member

jmanico commented Oct 20, 2024

I support that as well.

@elarlang
Copy link
Collaborator

The scope for this issue is 51.5.1. The goal of the requirement is to mitigate ID token replay attacks.

With PKCE you take down the vector, that the client can not ask for tokens from AS, with ID token nonce you take down the vector, that the client does not accept ID token, if it is not from the user's own authorization flow/transaction.

From a testing/verifying point of view - I would say, that the nonce solution, that is made for exactly that, is the first preferred option. If in practice I can not do the replay attack, then whatever defense works, including PKCE.

Where I'm wrong?

There is some discussion about levels. ID token replay, requirement 51.5.1, and PKCE usage, requirement 51.2.3 - both are level 1 at the moment.

@jmanico
Copy link
Member

jmanico commented Oct 20, 2024

PKCE was originally designed to prevent authorization code injection bit it does have an indirect benefit of stopping some replay attacks. PKCE adds valuable security, but it shouldn’t be seen as the main line of defense for ID token replay in the context of 51.5.1.

From a testing perspective, the nonce solution seems preferred - since it directly stops ID token replay. But as you said, if a defense (like PKCE) blocks the replay attack in practice, it’s still valid, even if it's not targeted a lot.

Both requirements (51.5.1 for ID token replay and 51.2.3 for PKCE) are level 1 because they address serious risks but in slightly different contexts. I'd say this makes sense.

I am just trying to see if I can reading your comments right, are we in sync?

@elarlang
Copy link
Collaborator

Your translation from my comments is ok. But I can not understand the problem to solve here.

This is the requirement as it stands:

# Description L1 L2 L3
51.5.1 [ADDED] Verify that the Client (as the relying party) mitigates ID token replay attacks. For example, by ensuring that the 'nonce' claim in the ID token matches the 'nonce' value sent in the authentication request to the OpenID provider (in OAuth2 refereed to as the authorization request sent to the authorization server).

From the comments above, I'm not convinced we need to change the requirement to have PKCE focus as the 1st option. PKCE is required for code flow anyway from level 1 by 51.2.3.

@jmanico
Copy link
Member

jmanico commented Oct 20, 2024

I would consider adding this to the end of 51.5.1

Additionally, while PKCE primarily protects against authorization code injection, it can also provide an extra layer of defense by securing the authorization code exchange, indirectly helping to mitigate some replay attacks.

@elarlang
Copy link
Collaborator

It is already long and it's going to cheat sheet side already. The only required part of the requirement is:

Verify that the Client (as the relying party) mitigates ID token replay attacks.

If the requirement is not wrong or we are not against any best practices or recommendation, I prefer to stay with that requirement as it is.

ping @randomstuff @TobiasAhnoff

@jmanico
Copy link
Member

jmanico commented Oct 20, 2024

I think that's fair Elar. I do not think it really needs to be added. I was just throwing that in there in case you or others want it.

@TobiasAhnoff
Copy link

51.5.1 may not need to change, but I still feel it is unclear that when using a backend client with code+PKCE there is no need to validate ID Token nonce, a suggestion is to have

If ID token in front-channel, verify that the Client (as the relying party) mitigates ID token replay attacks. For example, by ensuring that the 'nonce' claim in the ID token matches the 'nonce' value sent in the authentication request to the OpenID provider (in OAuth2 refereed to as the authorization request sent to the authorization server).

@elarlang
Copy link
Collaborator

I think my comment (#2002 (comment)) is still valid. If I lack some important nuances here, please explain this during the meeting.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
1) Discussion ongoing Issue is opened and assigned but no clear proposal yet V51 Group issues related to OAuth Will be closed if no response/opposite arguments _5.0 - prep This needs to be addressed to prepare 5.0
Projects
None yet
Development

Successfully merging a pull request may close this issue.

6 participants