-
Notifications
You must be signed in to change notification settings - Fork 44
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
[QUESTION] Support for customizing default verification #147
Comments
Valid request! Thanks for posting. We need some time to research this and form an opinion. Thanks for your suggestions and ideas, that's very helpful. |
Excuse the long wait. Q: what work around have you employed for now? |
@ottokruse I implement a verification of JWT with more low level library jose. This is part of the code that's actually being used in the service. import { createRemoteJWKSet, errors, jwtVerify } from 'jose'
async function retrieveCognitoId(request: Request) {
if (!request.token) {
throw new UnauthorizedError()
}
try {
const decoded = await jwtVerify(request.token, await getJwks())
return decoded.payload.sub
} catch (e) {
if (e instanceof errors.JWTExpired) {
throw new UnauthorizedError('Token has expired')
}
}
throw new UnauthorizedError()
}
let _jwks: ReturnType<typeof createRemoteJWKSet>
async function getJwks(): Promise<typeof _jwks> {
if (!_jwks) {
const jwksUrl = await getCognitoJwksUrl()
_jwks = createRemoteJWKSet(
new URL(jwksUrl),
{ cacheMaxAge: 1000 * 60 * 60 * 24 }, // 24 hours
)
}
return _jwks
}
async function getCognitoJwksUrl(): Promise<string> {
const endpoint = settings.cognitoEndpoint ?? `https://cognito-idp.${await cognito.config.region()}.amazonaws.com/`
const userPoolId = settings.cognitoUserPoolId
// refs) https://docs.aws.amazon.com/ja_jp/cognito/latest/developerguide/amazon-cognito-user-pools-using-tokens-verifying-a-jwt.html
return `${endpoint}${userPoolId}/.well-known/jwks.json`
} |
Thanks for the info! What you do can also be done with the import { JwtVerifier } from "aws-jwt-verify";
import { validateCognitoJwtFields } from "aws-jwt-verify/cognito-verifier";
// define at this scope to retain JWKS cache across invocations of retrieveCognitoId:
const verifier = JwtVerifier.create({
issuer: "https://cognito-idp.eu-west-1.amazonaws.com/<user_pool_id>", // in test, put the test iss here
jwksUri: await getCognitoJwksUrl(), // top level await does require ESM
audience: null, // audience (~clientId) is checked instead, by the Cognito specific checks below
customJwtCheck: ({ payload }) =>
validateCognitoJwtFields(payload, {
tokenUse: "access", // set to "id" or "access" (or null if both are fine)
clientId: "<client_id>", // in test put the test client id here
}),
});
async function retrieveCognitoId(request: Request) {
return verifier.verify(request.token).then(payload => payload.sub)
}
// unchanged:
async function getCognitoJwksUrl(): Promise<string> {
const endpoint = settings.cognitoEndpoint ?? `https://cognito-idp.${await cognito.config.region()}.amazonaws.com/`
const userPoolId = settings.cognitoUserPoolId
// refs) https://docs.aws.amazon.com/ja_jp/cognito/latest/developerguide/amazon-cognito-user-pools-using-tokens-verifying-a-jwt.html
return `${endpoint}${userPoolId}/.well-known/jwks.json`
} I think that's the best we can and should do to cater for your scenario--to keep the CognitoJwtVerifier as simple, and thus secure (prevents accidental misuse), as we can. Let us hear your thoughts please. |
That's documented here: Using the generic JWT verifier for Cognito JWTs |
Question
Would it be acceptable to add a support for customizing default verification?
Thanks in advance for develop and maintenance this great library!
This save me from many complex lines and common mistakes.
Btw, I use the emulator of cognito in local development environment (and real cognito in production).
It works with container and in local endpoint (ex,
http://localhost:9229
).I want to use
aws-jwt-verify
with it , but there are some issues.jwksUri: settings.cognitoEndpoint && `${settings.cognitoEndpoint}/.well-known/jwks.json`
local_xxxxxx
with the emulator, and user-pool-id verification is failed.http://localhost:9229/
with the emulator, and issuer verification is failed.I'm happy if I can handle these with
aws-jwt-verify
in some way.There are some possible solutions, but I think most of those are more or less emulator-specific.
For example,
CognitoJwtVerifier
receivecustomEndpoint
as a parameter, and use it as endpoint ofjwksUri
and issuer verificationjwksUri
customEndpoint
is specified, skip user-pool-id verificationSo, I think well new feature is
CognitoJwtVerifier
receivecustomUserPoolIdCheck
customIssuerCheck
and override default behaviorcustomDefaultCheck
and override all default check.I understand and agree that
aws-jwt-verify
should focus on real AWS services.This feature weaken security with wrong use so I'm wondering if it is acceptable.
On the other hand, many aws-sdk clients are basically support for
customEndpoint
and can use with several emulators.I would be happy if
aws-jwt-verify
can use with them :)Versions
Which version of
aws-jwt-verify
are you using?4.0.0
Are you using the library in Node.js or in the Web browser?
Node.js
If Node.js, which version of Node.js are you using? (Should be at least 14)
18.12.1
If Web browser, which web browser and which version of it are you using?
If using TypeScript, which version of TypeScript are you using? (Should be at least 4)
5.1.6
The text was updated successfully, but these errors were encountered: