Michael Lorton
Michael Lorton

Reputation: 44426

How do I verify a JWT with JWKS-RSA?

This strikes me as the intuitive way to use Kinde to sign in, but maybe it just isn’t possible.

I have a front-end, built in React. It successfully communicates with Kinde to log the user in and a the Kinde hook can retrieve both the “token” and the “id-token”.

I can pass that token to the Node backend, where I want to validate it — that is the whole point, of course.

The backend can access the /.well-known/jwks.json and get info about the key, including what certainly looks like a public key.

  {
    "e": "AQAB",
    "n": "yM9aMk..._UH5aBW6Aw",
    "alg": "RS256",
    "kid": "1a:66:bd:ac:50:86:8d:59:af:d1:e0:ee:52:60:95:3a",
    "kty": "RSA",
    "use": "sig"
  }
]

The problem is, when I try to extract the “signing key”, using jwksClient from jwks-rsa deep in something called “jose” throws a CryptoKey is not extractable. exception.

How can I do this simplest-case thing?

Upvotes: 0

Views: 251

Answers (1)

Michael Lorton
Michael Lorton

Reputation: 44426

So I posted this question and 10 minutes later found the answer:

 import { JwtRsaVerifier } from 'aws-jwt-verify'

 const verifier = JwtRsaVerifier.create(
    {
      issuer,
      audience: null,
      jwksUri: `${issuer}/.well-known/jwks.json`,
    });

  ...
  verifier.verify(token)

So I went to bed. The next morning... it had stopped working. More specifically, it was always timing out. Cue another hour of screwing around figuring how to change the timeout, ending up with:

  import { JwtRsaVerifier } from 'aws-jwt-verify'
  import { JwtPayload } from 'aws-jwt-verify/jwt-model'
  import { SimpleJwksCache } from 'aws-jwt-verify/jwk'
  import { SimpleJsonFetcher } from 'aws-jwt-verify/https'

  const verifier = JwtRsaVerifier.create(
    {
      issuer,
      audience: null,
      jwksUri: `${issuer}/.well-known/jwks.json`,
    },
    {
      jwksCache: new SimpleJwksCache({
        fetcher: new SimpleJsonFetcher({
          defaultRequestOptions: { timeout: 2000 },
        }),
      }),
    }
  )
  ...
  verifier.verify(token)

The fact that Kinde cannot reliable open a connection in 500ms is worrying, but it’s their problem not mine. If I get a chance, I will submit a PR to the aws-jwt-library exposing timeout as a top-level option.

Upvotes: 0

Related Questions