Parse a JWT Token issued by a Java application, inside a python script

493 Views Asked by At

I have a Java Spring boot API that a user logs in and is issued a JWT token ( i cant change this code). I have a new python API that needs to parse the JWT to verify its been authenticated.

Java Code

import io.jsonwebtoken.Jwts;

   private String secretKey = "CFB86D5E4DC4C11C6AFA9E5DF5AD9"

   String jwt = Jwts.builder()
          .setSubject(userByUsername.getUsername())
          .setIssuedAt(now)
          .setNotBefore(now)
          .setIssuer("my-authenticator")
          .setExpiration(new Date(System.currentTimeMillis() + (1000L * tokenMaxAge)))
          .signWith(SignatureAlgorithm.HS256, secretKey)
          .compact();

Inside my python code i have

import jwt

    token = "eyJhbGciOiJIUzI1NiJ9.eyJzdWIiOiJhZG1pbiIsImlhdCI6MTY3NDUwMzE2NSwibmJmIjoxNjc0NTAzMTY1LCJpc3MiOiJ0ZXN0IiwiZXhwIjoxNjc0NTA2NzY1fQ.wPc98PTVmZKKUEBmuKZG3Z_fXrC7QLLpLE9BXHR3Sw4"
    key = 'CFB86D5E4DC4C11C6AFA9E5DF5AD9'

    jwt_options = {
        'verify_signature': True,
        'verify_exp': False,
        'verify_nbf': False,
        'verify_iat': True,
        'verify_aud': False
    }

    parts = jwt.decode(token, key, algorithms="HS256", options=jwt_options)

    print(parts)

If I set verify_signature = False everything works and i can parse the jwt. But I need to have this set to true. If I go to jwt.io the signature shows up as verified enter image description here I've tried playing around with encoding/decoding the string but Im not sure what I'm missing

I have tried decoding and encoding the key but havn't had success. The secret is the same in the java application and python application

ex1. key = b'CFB86D5E4DC4C11C6AFA9E5DF5AD9'

ex2. key = str(base64.urlsafe_b64decode(CFB86D5E4DC4C11C6AFA9E5DF5AD9), 'utf-8')

ex3. key = base64.urlsafe_b64decode(CFB86D5E4DC4C11C6AFA9E5DF5AD9)

ex4. key = base64.b64decode('CFB86D5E4DC4C11C6AFA9E5DF5AD9') # this gives binascii.Error: Invalid base64-encoded string: number of data characters (29) cannot be 1 more than a multiple of 4

Solution:

So I was able to solve my question but im not sure why it worked. The first consisted of setting my secret to a 256 character string ex. 73357638792F423F4428472B4B6250655368566D597133743677397A24432646 The next step was to encode it to UTF-8 and then b64encode it so:

 jwt_options = {
     'verify_signature': True,
     'verify_exp': False,
     'verify_nbf': False,
     'verify_iat': True,
     'verify_aud': False
 }

 signature_key = config.config.signature_key
 signature_key = b64decode(signature_key.encode("utf-8"))

 parts = jwt.decode(self.token, signature_key, algorithms=["HS256"], options=jwt_options)

0

There are 0 best solutions below