JWT Decoder
Decode JWT tokens safely in your browser. Inspect headers and payloads without sacrificing privacy.
Privacy Guaranteed
Your JWT token is decoded locally in your browser and is not uploaded anywhere.
Features
- 100% Client-Side Privacy: Decodes tokens directly in your browser using native JavaScript. Your sensitive JWT never hits any external server or API.
- Visual Tri-Part Separation: Clear, color-coded inspection panels separating the Header (Algorithm & Type), Payload (Claims & Data), and Signature.
- Registered Claims Recognition: Automatically parses standard RFC 7519 claims like
sub,iss,aud, andexp. - Full Unicode & UTF-8 Support: Correctly decodes payload objects containing accented characters, international scripts, and emoji.
- Real-Time Instant Parsing: Simply paste your token string to view formatted JSON with syntax highlighting and instant error diagnosis.
- Developer Ecosystem: Works seamlessly with our Base64 Converter, Timestamp Converter, and JSON Formatter.
How it works
A JSON Web Token (JWT) is composed of three distinct segments separated by periods (.): a Header, a Payload, and a Signature. Both the Header and Payload are Base64URL encoded JSON objects.
Paste your token into the input area above. The decoder splits the string, normalizes the Base64URL characters, and reconstructs the human-readable JSON payload. Because this is an inspection tool, it decodes the payload without requiring your private cryptographic keys. For a complete deep-dive into token verification and architecture, read our guide on What Is a JWT? or explore How to Validate JWT Expiration.
The Anatomy of a JSON Web Token (RFC 7519)
A JSON Web Token (JWT) is a compact, URL-safe means of representing claims to be transferred between two parties. Compact JWT strings follow a strict 3-part layout:
- Header: Contains the token metadata, typically the signing algorithm (
alg, e.g. HS256 or RS256) and the token type (typ: "JWT"). - Payload: Contains the claims—statements about an entity (typically, the user) and additional metadata such as expiration and issuer.
- Signature: Cryptographic hash calculated by signing the Base64URL encoded header and payload using the specified algorithm and a secret or private key.
Standard JWT Claims Reference (RFC 7519)
The IETF specification reserves seven standard claims for interoperable authentication and authorization:
| Claim | Full Name | Type | Description & Validation |
|---|---|---|---|
| iss | Issuer | String / URI | Identifies the principal that issued the token (e.g. https://auth.example.com). |
| sub | Subject | String | The principal that is the subject of the JWT (typically a unique user or service ID). |
| aud | Audience | String / Array | Identifies the target recipients or API services that should accept the token. |
| exp | Expiration Time | NumericDate (seconds) | Unix timestamp after which the token must be rejected. Crucial for token lifetimes. |
| nbf | Not Before | NumericDate (seconds) | Unix timestamp before which the token must not be accepted for processing. |
| iat | Issued At | NumericDate (seconds) | Unix timestamp indicating the exact time the token was originally created. |
| jti | JWT ID | String | Unique identifier for the token. Often used to prevent replay attacks and implement revocation lists. |
How to Decode & Verify JWTs in Code
Production applications must verify signatures and expiration timestamps on the server side:
Node.js (jsonwebtoken)
import jwt from "jsonwebtoken";
// Verifying signature and expiration together
try {
const decoded = jwt.verify(token, process.env.JWT_SECRET!, {
algorithms: ["HS256"],
issuer: "https://auth.example.com",
});
console.log("Authenticated User ID:", decoded.sub);
} catch (err) {
console.error("Invalid or expired token:", err.message);
}Python (PyJWT)
import jwt
try:
payload = jwt.decode(
token,
key="your-256-bit-secret",
algorithms=["HS256"],
options={"require": ["exp", "iss"]}
)
print("User ID:", payload["sub"])
except jwt.ExpiredSignatureError:
print("Token has expired.")
except jwt.InvalidTokenError:
print("Invalid token signature or format.")Go (golang-jwt)
package main
import (
"fmt"
"github.com/golang-jwt/jwt/v5"
)
func validateToken(tokenString string, secretKey []byte) (*jwt.MapClaims, error) {
token, err := jwt.Parse(tokenString, func(token *jwt.Token) (interface{}, error) {
if _, ok := token.Method.(*jwt.SigningMethodHMAC); !ok {
return nil, fmt.Errorf("unexpected signing method: %v", token.Header["alg"])
}
return secretKey, nil
})
if claims, ok := token.Claims.(jwt.MapClaims); ok && token.Valid {
return &claims, nil
}
return nil, err
}JWT Security Checklist for Developers
- Never Put Secrets in the Payload: Passwords, API secret keys, and personal identifying data (PII) should never reside in unencrypted JWT claims.
- Enforce Short Expiration Lifetimes: Access tokens should typically expire within 10–15 minutes. Pair with secure HTTP-only refresh tokens for session renewal.
- Explicitly Check the Algorithm Header: Whitelist expected algorithms (e.g.
algorithms: ["RS256"]) to preventalg: "none"bypass exploits. - Account for Clock Skew: Allow a small tolerance (e.g. 30–60 seconds) when comparing timestamps across distributed servers to prevent premature expiration errors.
Related Tools & Tutorials
What Is a JWT?
Complete beginner-to-advanced guide covering tokens, signing keys, and stateless authentication.
JWT Expiration Guide
Deep dive into the exp claim, clock skew handling, and backend middleware validation patterns.
Base64 Converter
Encode or decode Base64 and Base64URL text strings and binary image files.
Timestamp Converter
Convert JWT NumericDate seconds into ISO 8601 strings and local human-readable time.
Frequently Asked Questions
What is the difference between decoding and verifying a JWT?
Decoding merely reverses the Base64URL encoding so human developers can read the JSON header and payload claims. It does not check if the token was tampered with. Verifying a JWT requires applying a secret key (for HMAC algorithms like HS256) or a public key (for RSA/ECDSA algorithms like RS256/ES256) to confirm that the signature is mathematically valid and originated from a trusted issuer.
Can a JWT be decoded without a secret key?
Yes. In standard JSON Web Tokens (JWS), the header and payload are only encoded, not encrypted. Anyone who intercepts or possesses the token string can decode and read its payload claims. Confidentiality requires encrypting the token using JSON Web Encryption (JWE).
How is the exp (expiration) timestamp represented in a JWT?
The 'exp' claim is defined by RFC 7519 as a NumericDate: a Unix epoch timestamp measured in seconds (not milliseconds) since January 1, 1970 UTC. To convert it in JavaScript, multiply by 1,000 before passing it to new Date(exp * 1000).
Is it safe to paste my production tokens into this debugger?
Yes. All decoding runs purely client-side inside your browser sandbox. DevToolkit does not transmit, log, store, or forward tokens anywhere. However, as general security hygiene, you should avoid pasting production tokens containing elevated administrative privileges on shared or unmanaged computers.
What is the difference between HS256 and RS256?
HS256 (HMAC with SHA-256) is a symmetric algorithm where both the token issuer and the verifier share the same secret key. RS256 (RSA Signature with SHA-256) is an asymmetric algorithm where the auth server signs tokens with a private key, and API services verify them using a public key (often published via JWKS).
Why does my token fail to decode?
A valid compact JWT must contain exactly two periods (.) separating three segments: header.payload.signature. Common causes of errors include copying extra whitespace, missing trailing characters, or pasting an opaque access token instead of a structured JWT.