- changed status to open
JwksDecryptionKeyResolver does not support resolving OKP keys for ECDH-ES (or ECDH-ES with key wrapping)
I’m trying to use JwksDecryptionKeyResolver
with an OctetKeyPairJsonWebKey
decryption key to decrypt a signed and encrypted JWT using Ed25519 and X25519. I’ve tried the most obvious usage I can think of, but the key resolver will not select the key, even when the key ID is an exact match.
I’ve attached some code that can be used to reproduce the issue.
I’ve done some debugging, and it seems like the issue is caused by the key type being explicitly set to "EC"
in the filter created internally by JwksDecryptionKeyResolver
. This is because the key type is pulled from the algorithm, and both EcdhKeyAgreementAlgorithm
and EcdhKeyAgreementWithAesKeyWrapAlgorithm
have a fixed key type of EllipticCurveJsonWebKey.KEY_TYPE
.
As far as I understand, OKP keys are also a valid choice for ECDH-ES. Is there any way to get around this without writing a custom decryption key resolver?
Comments (8)
-
repo owner -
repo owner Hi Erin - Thanks for finding/raising this and the debugging and detailed explanation. There’s indeed a defect here, which looks like something that was overlooked when adding X25519 etc support from RFC 8037 with
#72. Unfortunately, fixing it is going to be a little awkward because RFC 8037 kinda breaks the assumption from the original JOSE RFCs that an alg implied a single kty. But I’ll try and do something that’s not too ugly.In the meantime, I’m afraid a custom decryption key resolver is probably what you’ll have to do. Here’s a simple example of one in a snippet of the reproduction code you provided:
... new JwtConsumerBuilder() .setDecryptionKeyResolver(new DecryptionKeyResolver() { private final List<JsonWebKey> jsonWebKeys = List.of(encryptionKey); @Override public Key resolveKey(JsonWebEncryption jwe, List<JsonWebStructure> nestingContext) throws UnresolvableKeyException { SimpleJwkFilter filter = new SimpleJwkFilter(); String kid = jwe.getKeyIdHeaderValue(); if (kid != null) { filter.setKid(kid, SimpleJwkFilter.VALUE_REQUIRED); } List<JsonWebKey> filtered = filter.filter(jsonWebKeys); return ((PublicJsonWebKey) filtered.get(0)).getPrivateKey(); } }) // Uncomment the following line to demonstrate that the token is valid // .setDecryptionKey(encryptionKey.getPrivateKey()) .setVerificationKeyResolver(new JwksVerificationKeyResolver(List.of(signingKey))) ...
-
repo owner - changed status to resolved
fa33e980f158ac876348402c6f025403f4e6a51a addresses this
-
reporter Thanks Brian, appreciate the help, and looking forward to the next release!
-
Thanks for the thanks Erin. The next release is on its way.
-
repo owner - changed status to closed
fixed in the -0.9.5 release
-
reporter Tried it out, and confirmed that it’s working nicely for my use case 🎉
-
Glad to hear it, thanks for the update!
- Log in to comment