-
-
Notifications
You must be signed in to change notification settings - Fork 262
feat(gotrue): introduce getClaims method to verify and extract JWT claims #1246
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
base: main
Are you sure you want to change the base?
Conversation
…aims This introduces a new `getClaims` method that supports verifying JWTs (both symmetric and asymmetric) and returns the entire set of claims in the JWT payload. Key changes: - Add `getClaims()` method to GoTrueClient for JWT verification and claims extraction - Implement base64url encoding/decoding utilities (RFC 4648) - Add JWT types: JwtHeader, JwtPayload, DecodedJwt, GetClaimsResponse - Add helper functions: decodeJwt() and validateExp() - Add AuthInvalidJwtException for JWT-related errors - Include comprehensive tests for getClaims, JWT helpers, and base64url utilities The method verifies JWTs by calling getUser() to validate against the server, supporting both HS256 (symmetric) and RS256/ES256 (asymmetric) algorithms. Note: This is an experimental API and may change in future versions. Ported from: supabase/auth-js#1030 🤖 Generated with [Claude Code](https://claude.com/claude-code) Co-Authored-By: Claude <[email protected]>
Following up on the initial getClaims implementation, this commit: - Removes experimental status from getClaims() method - Adds GetClaimsOptions class with allowExpired parameter - Updates getClaims() to accept optional options parameter - Improves documentation to better describe the method's behavior - Exports helper functions (decodeJwt, validateExp) for public use - Adds tests for allowExpired option The allowExpired option allows users to extract claims from expired JWTs without throwing an error during expiration validation. This is useful for scenarios where you need to access JWT data even after expiration. Ported from: supabase/auth-js#1078 🤖 Generated with [Claude Code](https://claude.com/claude-code) Co-Authored-By: Claude <[email protected]>
Updates getClaims() documentation and comments to clarify that the method always uses server-side verification via getUser(). This approach gracefully handles edge cases such as: - Key rotation scenarios where JWKS cache might not have the new signing key - Symmetric JWTs (HS256) that require server-side verification - Revoked or invalidated tokens that are still unexpired This aligns the implementation intent with the auth-js behavior where getClaims() falls back to getUser() when the signing key is not found in JWKS or when client-side verification is not available. The Flutter implementation uses this server-side verification approach for all JWT types, providing robust and consistent validation regardless of the signing algorithm. Related: supabase/auth-js#1080 🤖 Generated with [Claude Code](https://claude.com/claude-code) Co-Authored-By: Claude <[email protected]>
Fixed the _base64ToBase64url method to preserve padding characters when pad=true is specified. Previously, padding was always stripped during conversion, causing encode(data, pad: true) to return unpadded output. 🤖 Generated with [Claude Code](https://claude.com/claude-code) Co-Authored-By: Claude <[email protected]>
Pull Request Test Coverage Report for Build 18412233238Warning: This coverage report may be inaccurate.This pull request's base commit is no longer the HEAD commit of its target branch. This means it includes changes from outside the original pull request, including, potentially, unrelated coverage changes.
Details
💛 - Coveralls |
} | ||
|
||
final signingKey = | ||
(decoded.header.kid == null || decoded.header.alg.startsWith('HS')) |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
This case here can't be the case here anymore, right? If the token is symmetric getUser()
would already have been called and returned.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Yeah, this check doesn't make sense, it always evaluate to false.
I've change the condition to better align with JS implementation, so it only calls getUser
once.
_jwksCachedAt = now; | ||
|
||
// find the signing key | ||
return jwks.keys.firstWhereOrNull((jwk) => jwk.kid == kid); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
The js sdk throws an exception if no jwk could have been found, and I think we should do the same, because a missing public key with an asymmetric token is not solvable, right?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Where it throwing? I'm following this implementation https://github.com/supabase/supabase-js/blob/master/packages/core/auth-js/src/GoTrueClient.ts#L3380
Summary
This PR ports the
getClaims
method from supabase/auth-js#1030 to the Flutter client. The method supports verifying JWTs (both symmetric and asymmetric) and returns the entire set of claims in the JWT payload.Close #1117
Changes
getClaims()
method inGoTrueClient
for JWT verification and claims extractionJwtHeader
,JwtPayload
,DecodedJwt
,GetClaimsResponse
decodeJwt()
andvalidateExp()
AuthInvalidJwtException
for JWT-related errorsImplementation Details
The method handles different JWT signature algorithms:
getUser()
call - we cannot verify HMAC signatures client-side without the secret keyUsage Example
Related
🤖 Generated with Claude Code