JWT Decoder
Paste any JWT and instantly read its header and payload as pretty-printed JSON, plus the signature and token metadata. Decoding is pure base64url — no network calls, no secret needed. Local, private and useful for debugging auth flows.
Paste a token like header.payload.signature and each segment is decoded from base64url. Standard claims (iat, exp, sub…) are surfaced in their own table with human-readable dates.
Paste a JWT
Learn more
The three parts of a JWT
A JSON Web Token is three base64url-encoded segments joined by dots: header.payload.signature. Base64url is a small variant of standard Base64 that swaps + and / for - and _ and drops the trailing = padding, specifically so the result is safe to put directly in a URL or an HTTP header without further encoding — that's the detail that makes JWT-shaped strings instantly recognizable.
The header is a small JSON object naming the signing algorithm (alg) and token type (typ, almost always "JWT"). The payload is a JSON object of claims — the actual data the token carries, like who it identifies and when it expires. The signature is computed over the header and payload using the algorithm named in the header, and it's the only one of the three segments a decoder genuinely cannot make sense of without the signing key.
Registered claims worth knowing
RFC 7519 defines a small set of standard payload claims that most systems use, even though none of them are technically required. exp (expiration time) and nbf (not before) are Unix timestamps in seconds that bound when the token is valid; iat (issued at) records when it was minted. sub (subject) identifies who the token is about, usually a user ID; iss (issuer) identifies who created it; aud (audience) identifies who the token is intended for — a resource server should reject a token whose aud doesn't match itself, even if the signature is otherwise valid, since that's what stops a token minted for one service being replayed against another.
jti (JWT ID) is a unique identifier for the token itself, useful for tracking or revoking a specific token in a denylist. Anything beyond these registered claims is a "private" or "public" claim defined by whoever issued the token — there's no universal meaning to a field like role or permissions beyond what that specific system decided it means.
Symmetric vs. asymmetric signing
HS256 (HMAC with SHA-256) is symmetric: the same secret key both signs and verifies the token, which means every party that needs to verify a token must also hold a key capable of forging one. That's fine when there's exactly one issuer and one verifier under the same trust boundary — a single backend signing its own session tokens, for example.
RS256 (RSA with SHA-256) and its elliptic-curve counterpart ES256 are asymmetric: a private key signs, and a separate public key verifies. That distinction matters the moment more than one party needs to check a token's validity — an OAuth authorization server can publish its public key so any number of resource servers can verify tokens independently, without any of them being trusted with the ability to mint new ones. Public key rotation (via a JWKS endpoint) is also how large systems replace signing keys without invalidating every token that's currently in flight.
Why decoding is not the same as verifying
This is the single most important thing to understand about JWTs: anyone can decode a token's header and payload, because base64url is an encoding, not encryption — no key is needed to read them, only to check the signature is genuine. A tool like this one deliberately only decodes; it never claims a token is valid, because doing that safely requires the actual signing secret or public key, which should never be pasted into a browser tool.
This distinction had real consequences: in 2015, security researchers found that several popular JWT libraries would trust the alg field inside the token itself, including accepting alg: "none" as a valid, unsigned token — meaning an attacker could take any token, delete the signature, set alg to none, and have some server implementations accept it as legitimate. Modern libraries fixed this by requiring the verifier to specify which algorithms it will accept up front, rather than trusting whatever the token claims about itself — a good reminder that the payload of an unverified token is attacker-controlled data, not a trusted source of truth.
Why access tokens are usually short-lived
Because a JWT can't be edited or revoked once issued — there's no server-side session to delete, unlike a traditional session cookie — the standard mitigation is to keep the token's lifetime short, often just minutes, via the exp claim. A short-lived access token limits how long a stolen token stays useful, even if it can't be revoked directly.
That's what a separate, longer-lived refresh token is for: it's exchanged for a new short-lived access token when the old one expires, without forcing the user to log in again, and unlike the access token it's typically stored server-side or in a way that lets the issuer revoke it on logout or suspected compromise. Seeing both an access token and a refresh token in an auth flow isn't redundancy — they're solving two different problems, statelessness for the access token and revocability for the refresh token.
JWT decoder vs JWT verifier
A JWT decoder and a JWT verifier serve fundamentally different purposes, and conflating them is a common security mistake. A decoder simply reads the token: it splits the JWT into its three dot-separated segments, Base64Url-decodes the header and payload, and displays the resulting JSON. No signature check is performed. The claims you see — iss, sub, exp, custom claims — are presented exactly as they appear in the token, but a decoder gives you no guarantee that any of it is true. Anyone can craft a JWT with any payload; the encoding is not encryption and not authentication.
A verifier, by contrast, checks the token's signature against a known secret or public key (HMAC, RSA, or ECDSA depending on the alg header), validates standard claims like exp, nbf, aud, and iss, and rejects tokens that fail any check. Decoding is appropriate for debugging — inspecting what a token contains, checking claim values during development, or understanding an unfamiliar token format. Verification is required for any security decision: authenticating a user, authorizing an API request, or trusting identity claims. Never use a decoded-but-unverified token to make an access control decision; the signature is the only thing that distinguishes a legitimate token from a forged one.
Frequently asked questions
Can this tool verify that my JWT is valid?
No — verification requires the secret or public key that signed the token. This tool only decodes the three segments so you can inspect their contents.
Is decoding considered a security risk?
JWT payloads are base64-encoded, not encrypted. Anyone can read them; treat them as public data. Never put secrets in a token you share.
What do exp and iat mean in the payload?
iat (issued at) and exp (expiration) are Unix timestamps in seconds. The decoder shows both as human-readable dates so you can spot an expired token at a glance.
Want the background? Read the guide: What is a JWT?