(I’m doing this from Elixir, but I don’t think that makes any real difference to the use of the Erlang libraries)
I’ve got a JWT:
eyJhbGciOiJFUzI1NiIsInR5cCI6IkpXVCIsImtpZCI6IllkWVRDTEF4R0tXUmVWcmF1cVR6VmVwTlM2SHViM0NPT3Z1OHpvdk02SkkifQ.eyJzaWQiOiJjbTFxb2t6MjcwMWdkeXphdDc4MGIzNnhlIiwiaXNzIjoicHJpdnkuaW8iLCJpYXQiOjE3MjgyODYyODIsImF1ZCI6ImNtMW9tNmw5YjA2N3pwcjJrNXJqYTI5emEiLCJzdWIiOiJkaWQ6cHJpdnk6Y20xcHhvYTliMDBlbmx1ZnJjaWNsMDNoYyIsImV4cCI6MTcyODI4OTg4Mn0.d6adVWpxGpBjgctcxNGhl7JYifTJ2DuGQ7UgiyCgLAOaV2EEi93QdyIxaqIvJqE8MlWBUB75U7lkx7VDHVmkIA
And a public key:
-----BEGIN PUBLIC KEY-----
MFkwEwYHKoZIzj0CAQYIKoZIzj0DAQcDQgAEKb10T35LVhx3qRHe644XbRwY3ck/FvkuIcOrX1xQYmyUZZ4FcNKTF5L0e8K+eMgYur0hCl2JaPFjpAHG2EYzTA==
-----END PUBLIC KEY-----
https://jwt.io/ agrees that the signature matches with that public key. The basic process I’m using is:
[asn] = :public_key.pem_decode("-----BEGIN PUBLIC KEY-----
MFkwEwYHKoZIzj0CAQYIKoZIzj0DAQcDQgAEKb10T35LVhx3qRHe644XbRwY3ck/FvkuIcOrX1xQYmyUZZ4FcNKTF5L0e8K+eMgYur0hCl2JaPFjpAHG2EYzTA==
-----END PUBLIC KEY-----")
pubkey = :public_key.pem_entry_decode(asn)
signed = "eyJhbGciOiJFUzI1NiIsInR5cCI6IkpXVCIsImtpZCI6IllkWVRDTEF4R0tXUmVWcmF1cVR6VmVwTlM2SHViM0NPT3Z1OHpvdk02SkkifQ.eyJzaWQiOiJjbTFxb2t6MjcwMWdkeXphdDc4MGIzNnhlIiwiaXNzIjoicHJpdnkuaW8iLCJpYXQiOjE3MjgyODYyODIsImF1ZCI6ImNtMW9tNmw5YjA2N3pwcjJrNXJqYTI5emEiLCJzdWIiOiJkaWQ6cHJpdnk6Y20xcHhvYTliMDBlbmx1ZnJjaWNsMDNoYyIsImV4cCI6MTcyODI4OTg4Mn0"
signature = :base64url.decode("d6adVWpxGpBjgctcxNGhl7JYifTJ2DuGQ7UgiyCgLAOaV2EEi93QdyIxaqIvJqE8MlWBUB75U7lkx7VDHVmkIA")
true = :public_key.verify(signed, :sha256, signature, pubkey)
This process works fine for RS256 JWTs, and I have working code for EdDSA JWTs as well, but for some reason the final verify returns false here rather than true. I know that this particular JWT is now expired, that doesn’t matter for verifying the signature.
Presumably I’m doing something wrong, but I can’t work out what it might be