Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

How to verify JWT signed by keycloak using java

I have JWT generated by keyCloack, RS256 something like this

sample:

eyJhbGciOwia2lkIiA6ICJtSG1lajZEc09GaV9MejdSMjhzWjdMWkxBRXVzIn0.eyBzA2MzQvOTcwNjM1L1NNUyIsIi83Ni83NS9TTVMiXSwicHJYW1lIjoidGVzdDEwNUB1c2VyLmNvbSIsInVzZXJOYW1lIjoidGVzdDEwNUB1c2VyLmNvbSIsInVzZXJJZCI6IjU4NDM2NmQ4LWU5NDItNGJhNy04OGVlLWMyZTBlODhmZmY5ZCIsImVtYWlsIjoidGVzdDEwNUB1c2VyLmNvbSJ9.4TgC1MLyUl1P36oD6FafBCh0peEaCBmkyLheVjnlBu8uePl9xgEN6wdeWe

I need to decode and validate this token using keycloack certificate.

i can reach the keycloack certificate over api.

https://xxx.xxx.com.tr/auth/realms/myrealm/protocol/openid-connect/certs

in the response, I have x5c field.

{
    "keys": [
        {
            "kid": "j6DsCpPOz1RXJhtPR28sZ7LZLAEus",
            "kty": "RSA",
            "alg": "RS256",
            "use": "sig",
            "n": "m0oTFvyLhLGIciXfndxc7uhIKE2-q9nJQKByd0FVYe8Cd4CHDpTzzcYdPWRR-1_VKQ75wqpybRt-LnnTKPNCXrPtPDRn2GFihtYyyO8VjeVtnz-iYJJAHkdp25HlMtX9l-VjnQX9s70-lbMmCVCRTerw",
            "e": "AQAB",
            "x5c": [
                "MIICnTCCAYUCBgFzh2ZkQzANBgkqhkiG9w0BAQ50F/bO9PpWzJglQkU3q8CAwEAATANBgkqhkiG9w01faO/9ZzyiLMLsorUKzYPNAxc7Q9rLE0J2MCWfapx3/E4yyNjISuB1HpS5iF44OEhGHJlw7JQeogcZat0enB8yyXtP/cgBhCnrWwfugX8rHsWfHakBGdsoazR9w=="
            ],
            "x5t": "YF6LE97opzsTtD-yLNx9-Lo",
            "x5t#S256": "SdNCfMbCjvcq-JY3iiGAj7De9Hal_0Cck-bDFK3Ow"
        }
    ]
}

I can validate this jwt over https://jwt.io/ if I put the x5c part within ----CERTIFICATE----- tag

-----BEGIN CERTIFICATE-----
MIICnTCCAYUCBgFzh2ZkQzANBgkqhkiG9w0BAQ50F/bO9PpWzJglQkU3q8CAwEAATANBgkqhkiG9w01faO/9ZzyiLMLsorUKzYPNAxc7Q9rLE0J2MCWfapx3/E4yyNjISuB1HpS5iF44OEhGHJlw7JQeogcZat0enB8yyXtP/cgBhCnrWwfugX8rHsWfHakBGdsoazR9w==
-----END CERTIFICATE----- 

how can I verify same thing in Java?

I tried couple of things but it failed.

like image 652
sakirow Avatar asked Sep 20 '25 00:09

sakirow


2 Answers

I think you can use jose4j library for that.

HttpsJwks httpsJkws = new HttpsJwks("https://xxx.xxx.com.tr/auth/realms/myrealm/protocol/openid-connect/certs");
HttpsJwksVerificationKeyResolver httpsJwksKeyResolver = new HttpsJwksVerificationKeyResolver(httpsJkws);


// Use JwtConsumerBuilder to construct an appropriate JwtConsumer, which will
// be used to validate and process the JWT. But, in this case, provide it with
// the HttpsJwksVerificationKeyResolver instance rather than setting the
// verification key explicitly.

jwtConsumer = new JwtConsumerBuilder()
    // ... other set up of the JwtConsumerBuilder ...
    .setVerificationKeyResolver(httpsJwksKeyResolver)
    // ...
    .build();
like image 101
matejko219 Avatar answered Sep 21 '25 15:09

matejko219


I found the way.

First, we need to login keycloack console, you can reach the public key related with realm.

now you have publickey from keycloak and JWT from user.

you need to import related libraries first.

<dependency>
            <groupId>io.jsonwebtoken</groupId>
            <artifactId>jjwt-api</artifactId>
            <version>0.11.2</version>
        </dependency>
        <dependency>
            <groupId>io.jsonwebtoken</groupId>
            <artifactId>jjwt-impl</artifactId>
            <version>0.11.2</version>
            <scope>runtime</scope>
        </dependency>
        <dependency>
            <groupId>io.jsonwebtoken</groupId>
            <artifactId>jjwt-jackson</artifactId>
            <version>0.11.2</version>
            <scope>runtime</scope>
        </dependency>

after that here is the logic.

String token = "ghfghfdhdhdfhdfghdhdfhdfhdfhhdf";
String rsaPublicKey = "awdasdsadaefafafaef5df65d4f";
X509EncodedKeySpec keySpec = new X509EncodedKeySpec(Base64.getDecoder().decode(rsaPublicKey));
KeyFactory kf = KeyFactory.getInstance("RSA");
PublicKey = kf.generatePublic(keySpec);

we have publickey, we need to verify it

Jws<Claims> jwt = null;
try {
    jwt = Jwts.parserBuilder()
                        .setSigningKey(publicKey)
                        .build()
                        .parseClaimsJws(token);
            } catch (Exception e) {
                // if you get error, that means token is invalid.
            }
like image 30
sakirow Avatar answered Sep 21 '25 16:09

sakirow