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

release-23.2: CRDB-28040 : JWKS fetch from jwks_uri #119768

Merged

Conversation

BabuSrithar
Copy link
Contributor

@BabuSrithar BabuSrithar commented Feb 29, 2024

Backport 1/1 commits from #117054 on behalf of @BabuSrithar.

/cc @cockroachdb/release


Fixes CRDB-28040 ( JWKS fetch from jwks_uri )
This commit adds capability to fetch remote JWKS from issuer's jwks_uri endpoint. This will satisfy the requirement to have an ability to automatically fetch the new JWK when the existing JWK is rotated - without human intervention or custom scripts.

Changes include

  1. The existing order of token signature verification first and rest of claims next is modified to get issuer first and then the token signature verification. This change is requied to determine the issuer for which the jwks has to be fetched remotely.

  2. Introduction of a new cluster setting called server.jwt_authentication.jwks_auto_fetch.enabled

  3. Depending on the value of server.jwt_authentication.jwks_auto_fetch.enabled use JWKS configured through cluster setting or remotely fetch JWKS from jwks_uri of the issuer

  4. Modification to exiting test cases to match the new order of verification steps.

The change is backward compatible and not changes required in existing deployments and JWT Auth usage.

(cherry picked from commit 900408e)


Release justification: high-priority need for functionality in 23.2

@BabuSrithar BabuSrithar requested review from a team as code owners February 29, 2024 14:59
@cockroach-teamcity
Copy link
Member

This change is Reviewable

@dhartunian dhartunian changed the title CRDB-28040 : JWKS fetch from jwks_uri release-23.2: CRDB-28040 : JWKS fetch from jwks_uri Feb 29, 2024
@dhartunian
Copy link
Collaborator

dhartunian commented Feb 29, 2024

Thanks for opening a backport.

Please check the backport criteria before merging:

  • Backports should only be created for serious
    issues
    or test-only changes.
  • Backports should not break backwards-compatibility.
  • Backports should change as little code as possible.
  • Backports should not change on-disk formats or node communication protocols.
  • Backports should not add new functionality (except as defined
    here).
  • Backports must not add, edit, or otherwise modify cluster versions; or add version gates.
  • All backports must be reviewed by the owning areas TL and one additional
    TL. For more information as to how that review should be conducted, please consult the backport
    policy
    .
If your backport adds new functionality, please ensure that the following additional criteria are satisfied:
  • There is a high priority need for the functionality that cannot wait until the next release and is difficult to address in another way.
  • The new functionality is additive-only and only runs for clusters which have specifically “opted in” to it (e.g. by a cluster setting).
  • New code is protected by a conditional check that is trivial to verify and ensures that it only runs for opt-in clusters. State changes must be further protected such that nodes running old binaries will not be negatively impacted by the new state (with a mixed version test added).
  • The PM and TL on the team that owns the changed code have signed off that the change obeys the above rules.
  • Your backport must be accompanied by a post to the appropriate Slack
    channel (#db-backports-point-releases or #db-backports-XX-X-release) for awareness and discussion.

Also, please add a brief release justification to the body of your PR to justify this
backport.

@dhartunian dhartunian self-requested a review February 29, 2024 15:03
@@ -240,6 +240,15 @@ func jwtRunTest(t *testing.T, insecure bool) {
t.Fatalf("wrong number of comma separated argumenets to jwt_cluster_setting ident_map: %d", len(a.Vals))
}
pgwire.ConnIdentityMapConf.Override(context.Background(), sv, strings.Join(args, " "))
case "jwks_auto_fetch.enabled":
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I don't see this case added to any diffs in testdata. Am I missing something?

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The test cases related to this case has been added in pkg/ccl/jwtauthccl/authentication_jwt_test.go, not in the data driven. I added this case here for completeness and avoid missing definitions for data driven format.

if authenticator.mu.conf.jwksAutoFetchEnabled {
jwkSet, err = remoteFetchJWKS(ctx, issuerUrl)
if err != nil {
return errors.Newf("JWT authentication: unable to validate token")
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The original error is lost in these handlers. I know we want to avoid leaking sensitive information, but this will make debugging this feature more challenging. Is there a reason we didn't wrap the err here and elsewhere?

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This is the discussion that lead to removal of logging lines. I agree that in some cases it might make it difficult to debug the exact error, but it is inline with other error handlings in this file. I am open to consider an alternate solution and include if available. https://reviewable.io/reviews/cockroachdb/cockroach/117054#-Nne7jnh5oeb9srWuZw2

Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

in some other places (e.g. password checking), we use the AuthConn.LogAuthFailed() helper so the detailed failure can be logged internally, and we show a more generic message to the user who failed auth.

ac.LogAuthFailed(ctx, eventpb.AuthFailReason_USER_NOT_FOUND, err)

i don't think we have access to that logger in this part of the code. refactoring the code is possible, but i'd say can be done separately from this backport

Copy link
Collaborator

@dhartunian dhartunian left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

:lgtm:

Reviewable status: :shipit: complete! 1 of 0 LGTMs obtained (waiting on @BabuSrithar)


pkg/ccl/jwtauthccl/authentication_jwt.go line 173 at r1 (raw file):

Previously, BabuSrithar (BabuSrithar) wrote…

This is the discussion that lead to removal of logging lines. I agree that in some cases it might make it difficult to debug the exact error, but it is inline with other error handlings in this file. I am open to consider an alternate solution and include if available. https://reviewable.io/reviews/cockroachdb/cockroach/117054#-Nne7jnh5oeb9srWuZw2

Gotcha. Thanks.


pkg/ccl/testccl/authccl/auth_test.go line 243 at r1 (raw file):

Previously, BabuSrithar (BabuSrithar) wrote…

The test cases related to this case has been added in pkg/ccl/jwtauthccl/authentication_jwt_test.go, not in the data driven. I added this case here for completeness and avoid missing definitions for data driven format.

👍

@dhartunian dhartunian requested a review from rafiss March 5, 2024 15:11
if authenticator.mu.conf.jwksAutoFetchEnabled {
jwkSet, err = remoteFetchJWKS(ctx, issuerUrl)
if err != nil {
return errors.Newf("JWT authentication: unable to validate token")
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

in some other places (e.g. password checking), we use the AuthConn.LogAuthFailed() helper so the detailed failure can be logged internally, and we show a more generic message to the user who failed auth.

ac.LogAuthFailed(ctx, eventpb.AuthFailReason_USER_NOT_FOUND, err)

i don't think we have access to that logger in this part of the code. refactoring the code is possible, but i'd say can be done separately from this backport

@BabuSrithar
Copy link
Contributor Author

Have built 23.2 locally with this branch and tested following scenarios.

  1. JWT Authentication with and without server.jwt_authentication.jwks_auto_fetch.enabled, switching back and forth.
  2. OIDC Login through UI.

This commit adds capability to fetch remote JWKS from issuer's jwks_uri endpoint. This will satisfy the requirement to have an ability to automatically fetch the new JWK when the existing JWK is rotated - without human intervention or custom scripts.

Changes include

1. The existing order of token signature verification first and rest of claims next is modified to get issuer first and then the token signature verification. This change is requied to determine the issuer for which the jwks has to be fetched remotely.

2. Introduction of a new cluster setting called `server.jwt_authentication.jwks_auto_fetch.enabled`

3. Depending on the value of `server.jwt_authentication.jwks_auto_fetch.enabled` use JWKS configured through cluster setting or remotely fetch JWKS from jwks_uri of the issuer

4. Modification to exiting test cases to match the new order of verification steps.

The change is backward compatible and not changes required in existing deployments and JWT Auth usage.

(cherry picked from commit 900408e)
@BabuSrithar
Copy link
Contributor Author

Thanks for the review @dhartunian and @rafiss.

The Extended CI is failing on unlrealted tests and they are different random ones every time I re-run. Can you check if it is ok to merge this change ?

@BabuSrithar BabuSrithar merged commit 2fc2bbf into cockroachdb:release-23.2 Mar 7, 2024
5 of 6 checks passed
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

Successfully merging this pull request may close these issues.

None yet

4 participants