Authorization in a Nutshell: Deep dive into the JWT authentication.
JSON web token (JWT) is a modern standard authentication method, mostly adopted by the REST API and microservices. JWT allows a stateless authentication mechanism, which helps authorize multiple services from a single auth module. Let’s have a look at how the JWT authentication works.
JWT token structure
JWT is just a hashed version of the given payload in it. It has three separate parts with different datasets in it. Here is an example of JWT.
eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9.eyJzdWIiOiIxIiwibmFtZSI6IlV0cGFsIFNhcmthciIsImlhdCI6MTUxNjIzOTAyMn0.k3ZtaorE3fZ_yQBa1jeexExFHK9p5LsYlDMY-Sj1Y9E
Here you can see it has three separate parts separated by a dot (.). The first part of this token contains information about the hashing algorithm of the token like,
{
"alg": "HS256",
"typ": "JWT"
}
and the second part of this token contains payload provided by the application like in this token it has,
{
"sub": "1",
"name": "Utpal Sarkar",
"iat": 1516239022
}
and the last part is the signature, that signature is used for verifying the token validation. You can debug any JWT at JWT.IO.
JWT authentication process
It’s similar to the other token-based authentication, the main difference is that the JWT itself provides the data for verifying it’s validation. That means we can just decode the token by checking the signature and comparing the expiration time from the token payload, that’s it. The flow works like we get the authorization token from a request and check if it’s a valid JWT it has a valid signature and it’s not expired then the user is authorized, now we can get the user by ID we can get it from the sub
property of the token payload.
JWT implementation
Let’s have a real-world example in Nodejs,
Create a JWT
import { SignJWT } from "jose";
const token = new SignJWT(payload)
.setProtectedHeader({ alg: 'HS256' })
.setIssuedAt()
.setSubject(user_id)
.setExpirationTime('5h')
.sign('secret');
Validate a JWT
import { jwtVerify } from "jose";
const { payload } = await jwtVerify(token, 'secret');
console.log(payload);
const user = await User.findById(payload.id);
if(user) {
console.log("It's a valid JWT");
}