JWT Decoder (header, payload, signature, expiry)
Paste a JWT to instantly decode header and payload as JSON. Recognizes standard claims (iat, exp, nbf) and converts Unix timestamps to ISO 8601. Flags expired or not-yet-valid tokens.
Decoded entirely in your browser. The token never travels over the network.
Header
{
"alg": "HS256",
"typ": "JWT"
}Payload
{
"sub": "1234567890",
"name": "Jane Doe",
"iat": 1730000000,
"exp": 4886000000
}- Signature present
- ✓
- Issued at (iat)
- 2024-10-27T03:33:20.000Z
- Expires at (exp)
- 2124-10-30T22:13:20.000Z
How it works
What a JWT looks like
A JWT is three Base64url-encoded segments joined by dots: header.payload.signature. Each segment is a JSON object encoded for URL-safe transmission. The header declares the signing algorithm, the payload carries claims (subject, expiry, custom data), and the signature lets the recipient verify integrity if they have the key.
This decoder reads only the first two segments. The signature is the third segment but verifying it requires the secret/public key — that's a separate operation we don't perform here.
Standard claims worth knowing
iss (issuer): who created the token. iat (issued at): when, as Unix timestamp. exp (expiry): when it stops being valid, also Unix. nbf (not before): the earliest time it should be honored. sub (subject): the entity it represents, often a user ID. aud (audience): who the token is for, usually a service URL.
Not all are mandatory; minimal JWTs often have just sub + iat + exp. Custom claims are anything else — they live alongside the standard ones in the payload.
Why decoding ≠ verifying
Anyone can decode a JWT — the header and payload are just Base64-encoded JSON. That's why we say 'never put secrets in the payload': they're effectively public.
Verification means checking the signature against the secret key (HMAC) or public key (RSA/ECDSA). Without verification, you can't trust any claim inside the payload — an attacker can craft any payload they want.
Use this tool to inspect tokens during debugging. Use a JWT library on your server to verify them in production.
Frequently asked questions
›Can I verify the signature here?
No — verification needs the secret or public key, which should never leave a trusted environment. Use a server-side JWT library (jsonwebtoken for Node, PyJWT for Python, etc.).
›Does the token leave my browser?
Never. Decoding runs locally; we don't have a server endpoint to receive it.
›Why is my token 'invalid'?
Common: copy-paste added/removed whitespace, missing one of the three segments, or one segment is malformed Base64url. Trim and retry.
›What's Base64url vs Base64?
Base64url replaces '+' with '-', '/' with '_', and drops the '=' padding so the encoded string is safe in URLs and HTTP headers. JWTs always use Base64url.
›Why does my Unicode payload show garbled text?
We decode UTF-8, which is the standard. If the payload was encoded differently, the JSON.parse may fail. Most JWT issuers correctly encode UTF-8.
›Is HS256 secure?
If the secret is sufficiently long (≥256 bits) and kept secret, yes. Common HS256 vulnerabilities are weak secrets and accepting tokens with alg='none'. Use ≥32-character random secrets and reject 'none' explicitly.
›Why prefer RS256 over HS256?
RS256 (asymmetric RSA) lets you publish a public key for verification while keeping the signing key private. HS256 (symmetric HMAC) requires sharing the secret with every verifier. For multi-service architectures, RS256 is safer.
›Can I decode huge tokens?
Practical limit is ~10 MB of input; beyond that the browser may slow. JWTs are usually under 4 KB; if yours is larger, consider whether you're storing too much in claims.
Related tools
Last updated: