Creating Simple JSON Web Token(JWT) in Python

Introduction

JSON Web Token(JWT) is an open standard(RFC 7519) that defines a compact and self-contained way for securely transmitting information between parties as a JSON object.

JWT is a digitally signed web token that uses both Symmetric(one secret key) and Asymmetric(public and private keys) types of keys. It should be used during Authorization and Information Exchange over the network.

JWT structure contains three main parts:

a) Header: It consists of two fields: token type and algorithm.

{
  "alg": "HS256",
  "typ": "JWT"
}

b) Payload: It consists of an actual JSON object to be encoded.

c) Signature: It verifies the message wasn’t changed along the way by using the secret key shared between parties.

 

Implementation

Regarding generating web tokens, there exist dozens of Python libraries. Among them, we will use the PyJWT library in this blog post.

PyJWT is a Python library that allows us to encode and decode JSON Web Token(JWT).

Installation

$ pip install pyjwt

 

Let’s create two separate python files: encode.py and decode.py for the demonstration of JWT:

Inputs to be encoded in JWT

encode.py

# encode.py
import datetime
import jwt # import jwt library


SECRET_KEY = "python_jwt"

# json data to encode
json_data = {
    "sender": "CodeFires JWT",
    "message": "JWT is awesome. You should try it!",
    "date": str(datetime.datetime.now())
}

# encode the data with SECRET_KEY and 
# algorithm "HS256" -> Symmetric Algorithm
encode_data = jwt.encode(payload=json_data, \
                        key=SECRET_KEY, algorithm="HS256")

print(encode_data) # print the encoded token

Output:

eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJz.....

 

Note: The output token is truncated as it is lengthy.

Above we use jwt.encode function to generate web tokens using the Encoded format of inputs JWTHS256 algorithm with the secret key.

HS256 (HMAC with SHA-256), on the other hand, is a symmetric algorithm, with only one (secret) key that is shared between the two parties. Since the same key is used both to generate the signature and to validate it, care must be taken to ensure that the key is not compromised.

Instead of using HS256, we can also use HS512(symmetric) and RS256(asymmetric). Since we using the HS256 symmetric algorithm, the same key can be used for both encoding and decoding purposes.

 

decode.py

# decode.py
import jwt # import jwt library


SECRET_KEY = "python_jwt"

token = "eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1Ni...."

try:
    decode_data = jwt.decode(jwt=token, \
                            key=SECRET_KEY, algorithms="HS256")
    print(decode_data)
except Exception as e:
    message = f"Token is invalid --> {e}"
    print({"message": message})

Output:

{'sender': 'CodeFires JWT', 'message': 'JWT is awesome. You should try it!', 'date': '2021-10-14 11:00:22.684785'}

Above we used the same key to decode the generated token with the HS256 algorithm.

If the token is valid, then we get the correct JSON object else the python interpreter throws an exception as “Token is invalid …..”

 

The token obtains above is not time-bound means that it can be used again to get objects if provided with the correct secret key.

But if you want to make this token invalidate after some period of time, append another field as:

json_data = {
    "sender": "CodeFires JWT",
    .....
    # new field that make token invalidate after certain time
    'exp': datetime.datetime.utcnow() + datetime.timedelta(seconds=86400)
}

Here we make the generated token by the time of creation valid for 1 day which is 86400 seconds.

 

Conclusion

Hence, we successfully created simple JSON web tokens using the Python PyJWT library which encodes the data with a symmetric algorithm consisting of the secret key and decodes the token with the same key.

We can use that generated tokens to authorize the user during exploring the website that required login credentials for a certain period of time.

Happy Learning:-)

Leave a Comment