JWT Decoder Online Free — Inspect Token Claims & Expiry
The free JWT Decoder lets you paste any JSON Web Token and instantly see its decoded header, payload, all claims, and whether the token has expired. Everything is processed client-side — your token never leaves your browser.
What Is a JWT?
A JSON Web Token (JWT, pronounced “jot”) is a compact, URL-safe string used to represent claims between two parties. Standardised in RFC 7519 by the IETF in 2015, JWTs became the dominant format for stateless authentication tokens in web APIs and single-page applications.
In web development, JWTs are most commonly used as authentication tokens — a server issues a JWT after login, and the client sends it with each request as proof of identity. The server verifies the token's signature and reads the claims inside to authorize the request. Unlike traditional session cookies (which require the server to look up session state in a database), JWTs are self-contained — all the information needed to validate the user is inside the token.
A JWT consists of three Base64URL-encoded sections separated by dots:
- Header — algorithm and token type
- Payload — the claims (data)
- Signature — verifies that the token has not been tampered with
Base64URL is a URL-safe variant of Base64 that replaces + with -and / with _, and omits the = padding characters. This makes the token safe to include in URLs and HTTP headers without encoding.
Decoding a JWT reveals the header and payload in plain JSON. The signature can only be verified if you have the server's secret key — the decoder shows the raw signature bytes but cannot validate them without the key.
How to Decode a JWT
- Open the JWT Decoder
- Paste your JWT into the input field. It typically looks like:
eyJ…header….eyJ…payload….signature - The decoded header and payload appear immediately below
- Check the Expiry section to see whether the token is still valid, expired, or has no expiry set
JWT Claims Reference
| Claim | Full Name | Description |
|---|---|---|
iss | Issuer | Who created the token (e.g. your auth server URL) |
sub | Subject | The user or entity the token represents (typically a user ID) |
aud | Audience | Who the token is intended for (the API that should accept it) |
exp | Expiration | Unix timestamp after which the token is invalid |
iat | Issued At | Unix timestamp when the token was created |
nbf | Not Before | Token is invalid before this Unix timestamp |
jti | JWT ID | Unique identifier for the token (prevents replay attacks) |
Signing Algorithms — HS256 vs RS256 vs ES256
The JWT header always contains an alg field specifying the signing algorithm. The algorithm choice has significant security implications:
| Algorithm | Type | Keys | Use when |
|---|---|---|---|
HS256 | HMAC-SHA256 (symmetric) | One shared secret — both issuer and verifier use it | Monolithic applications where issuer and verifier are the same service |
RS256 | RSA-SHA256 (asymmetric) | Private key signs; public key verifies | Distributed systems where multiple services verify tokens; public key can be published |
ES256 | ECDSA-SHA256 (asymmetric) | Private key signs; public key verifies | Same as RS256 but with smaller key sizes and faster operations |
none | No signature | N/A — unsigned | Never use in production — allows attackers to forge arbitrary tokens |
The “algorithm confusion attack” is a well-known JWT vulnerability where an attacker changes the alg header from RS256 to HS256 and signs the token with the server's public key (which is publicly available). If the server code uses the same key for both algorithms, it accepts the forged token. Modern JWT libraries protect against this by requiring you to specify the expected algorithm, never accepting the algorithm stated in the header at face value.
JWT vs Session Cookies
| Aspect | JWT (stateless) | Session cookie (stateful) |
|---|---|---|
| Server storage | None — all data in the token | Session store (database, Redis, memory) |
| Scalability | Horizontal — any server can verify without shared state | Requires shared session store for multiple servers |
| Revocation | Difficult — JWT is valid until expiry unless a deny list is maintained | Easy — delete the session from the store |
| Token size | Larger — contains all claims in the token | Small — just a session ID |
| CSRF exposure | Lower if stored in memory (not cookies); higher if stored in cookies without SameSite | Standard CSRF protection required for cookie storage |
JWT Revocation — The Hard Problem
One of the most significant tradeoffs of JWTs is that they are self-contained — there is no built-in mechanism to revoke them before their expiry. If a user logs out or their access is revoked, a JWT they already possess remains valid until its expclaim passes.
Common patterns to manage this:
- Short expiry + refresh tokens: Issue short-lived access tokens (5–15 minutes) and longer-lived refresh tokens (hours/days). When the access token expires, the client exchanges the refresh token for a new one. Revocation invalidates the refresh token in the database, preventing new access tokens from being issued.
- Token deny list: Maintain a Redis or database list of invalidated JWT IDs (
jticlaims). Check each incoming token against the list. Eliminates the benefit of stateless tokens but enables immediate revocation. - Very short expiry: Accept that a compromised token is valid for a very brief window (30–60 seconds). Suitable for internal microservice communication where revocation is less critical.
Common JWT Debugging Scenarios
Token expired — 401 Unauthorized
The most common cause of unexpected 401 errors is an expired JWT. Paste the token into the decoder and check the exp claim. The tool converts the Unix timestamp to a human-readable date and shows whether the token is currently valid. If it has expired, the client needs to refresh or re-authenticate.
Wrong audience or issuer
If your API returns 403 Forbidden even with a valid, unexpired token, the server may be rejecting the token because the aud or iss claim does not match what it expects. Decode the token and compare these values against your API's expected issuer and audience configuration.
Missing claims
Authorization logic often reads custom claims from the payload — roles, permissions, tenant IDs. If a user is unexpectedly denied access, decode their token and confirm the relevant claim is present and has the expected value. This is much faster than adding debug logging and re-deploying.
Algorithm mismatch
The header contains an alg field specifying the signing algorithm — typically HS256, RS256, or ES256. If your server is configured to accept only one algorithm but the token uses another, verification will fail. Decode the header to confirm the algorithm matches your server's expectation.
Clock skew — token appears expired when it shouldn't be
JWT exp and iat timestamps are Unix seconds. If the clock on the issuing server and the verifying server drift by more than a few seconds, tokens may appear expired or “not yet valid” when they should be accepted. Most JWT libraries support a configurable clock skew tolerance (typically 30–60 seconds) to handle this. Check the raw exp timestamp in the decoder and compare it to the current Unix time to diagnose clock drift issues.
Security Note: Never Share Production Tokens
A JWT's payload is Base64-encoded but not encrypted — anyone with the token can decode and read its claims. Avoid pasting production tokens into any online tool, including this one, if the token grants access to real systems. Use test tokens or tokens from a development environment for debugging. This tool processes tokens entirely in your browser and sends nothing to a server, but the principle of not exposing production credentials to third-party tools applies regardless.
Decode JWTs Free Online
Inspect header, payload, claims, and expiry instantly. No server, no signup.
Open JWT Decoder