What Is a JWT Generator?
A JWT generator builds a signed JSON Web Token from a header and a payload. JWTs (RFC 7519) are the de-facto standard for stateless authentication on the web: a server issues one after a successful login, the client stores it, and every subsequent request includes it in an Authorization: Bearer ... header. The server then verifies the signature instead of looking up a session.
This tool generates signed tokens using HMAC algorithms — the symmetric variants of JWS (JSON Web Signature, RFC 7515). They are appropriate when both sides of a system share a secret: a backend signs, the same backend verifies. Asymmetric algorithms (RS256, ES256) are deliberately omitted because handling a private key in a browser is a recipe for accidental disclosure; sign those tokens on the server.
Anatomy of a JWT
A JWT is three base64url-encoded segments joined with dots:
eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9.eyJzdWIiOiIxIiwibmFtZSI6IkFsaWNlIn0.4Z7p...
└── header ────────────────────────┘ └── payload ────────────────────────┘ └ sig ┘
- Header — an object with the algorithm (
alg) and token type (typ: "JWT"). Optionallykid(key ID) when you rotate signing keys. - Payload — the claims object. Any JSON you want, plus optional standard claims (
iss,sub,aud,exp,nbf,iat,jti). - Signature —
HMAC(secret, base64url(header) + "." + base64url(payload))for HS-family algorithms.
The signature is what makes a JWT trustworthy. The payload itself is not encrypted — anyone who has the token can decode it. Don’t put passwords or PII in there.
How to Generate a JWT
- Paste a payload as JSON into the input panel. Use any claims you need (
sub,email,role,tenant_id, etc.). - Pick an algorithm in the settings panel —
HS256is the default and what 95% of systems use. - Enter a secret. For HS256 the secret should have at least 256 bits of entropy (32 random bytes). For HS512 use 512 bits. Don’t reuse a low-entropy passphrase.
- Click Generate (or press
Ctrl+Enter). The token appears in the output panel. - Copy with the Copy button or
Ctrl+Shift+Cand paste it into a header, a.envfile, an integration test, or whatever consumer needs it.
The expiration shortcuts (+15m, +1h, +1d, +7d) write a fresh exp claim into the payload before signing — convenient when you’re regenerating a test token in a hurry.
Standard Claims (RFC 7519)
| Claim | Purpose | Example |
|---|---|---|
iss | Issuer — who created the token | "auth.example.com" |
sub | Subject — who the token is about | "user_42" |
aud | Audience — who the token is for | "api.example.com" |
exp | Expiration (Unix seconds) | 1788196800 |
nbf | Not before (Unix seconds) | 1788193200 |
iat | Issued at (Unix seconds) | 1788193200 |
jti | Unique token ID | "a1b2c3..." (UUID) |
Custom claims sit alongside these. A common pattern is to namespace them with a URI or a short prefix (https://example.com/role, app:plan) to avoid collisions with future standard claims.
HS256 vs HS384 vs HS512
All three are HMAC over a SHA-2 hash. They differ only in the underlying hash:
| Algorithm | Hash | Signature length | Use when |
|---|---|---|---|
| HS256 | SHA-256 | 32 bytes | Default. What most libraries default to. |
| HS384 | SHA-384 | 48 bytes | Compliance regimes that mandate ≥384-bit hashes. |
| HS512 | SHA-512 | 64 bytes | Long-lived tokens where you want maximum margin. |
In practice, HS256 is fine for almost everything. The bottleneck is usually secret entropy, not hash output length — a 16-character password is the weak link, not the algorithm.
Common Mistakes and How to Avoid Them
- Storing JWTs in
localStoragefor browser apps. Any XSS leak exfiltrates the token. Prefer anHttpOnly; Secure; SameSitecookie. - Forgetting
exp. A JWT without expiration is forever-valid. If the secret leaks, every issued token is compromised until you rotate. Always setexp. - Trusting
algfrom the client. When verifying, hard-code the expected algorithm — never read it from the incoming token’s header. This is the class of bug behind the originalalg=noneexploits. - Putting secrets in the payload. The payload is base64url, not encrypted. Anyone with the token can read it. If you need confidentiality, use JWE or just don’t put the data in the token.
- Reusing the same secret across environments. Dev, staging, prod should each have a distinct signing key. A leaked dev key shouldn’t authenticate production users.
- Using an HMAC secret weaker than the hash. RFC 7518 §3.2 requires the key to be at least as long as the hash output. Generate
HS256secrets withopenssl rand -base64 32, not a memorable passphrase.
When NOT to Use JWTs
JWTs are great for stateless auth between services that already trust each other. They are not great when:
- You need server-side revocation. A signed token is valid until
exp. Rotating a single user out (after a password reset, account compromise, role change) requires either a denylist (which negates the stateless win) or short-lived tokens with a refresh dance. - Your tokens carry a lot of state. Every request ships every byte of the payload. Past ~1 KB you’re paying real bandwidth on every API call. A session cookie pointing to a Redis blob is leaner.
- You’re protecting cookies on the same origin. A plain session cookie is simpler, easier to revoke, and avoids the entire “where do I store the JWT” foot-gun.
JWT-shaped problems → JWT. Session-shaped problems → session cookie. Both are correct in their domain.
Verifying the Token
Generation is half the workflow — you also need to verify on the receiving side. In Node.js with the jose library:
import { jwtVerify } from 'jose';
const secret = new TextEncoder().encode(process.env.JWT_SECRET);
const { payload } = await jwtVerify(token, secret, {
algorithms: ['HS256'], // Lock the algorithm. Never trust `alg` from the header.
issuer: 'auth.example.com',
audience: 'api.example.com',
});
In Python with PyJWT:
import jwt
payload = jwt.decode(
token,
os.environ["JWT_SECRET"],
algorithms=["HS256"], # explicit allowlist
audience="api.example.com",
issuer="auth.example.com",
)
In every language, the rule is the same: always pass an explicit algorithms allowlist when verifying. Never let the token’s own header pick the algorithm.