ThisCalculator

Everyday

JWT 401 in Production: 5 Checks to Find the Mismatch

Updated · Standard formula, shown below

JWT 401 in Production: 5 Checks to Find the Mismatch

When a JWT-based API suddenly returns 401 in production, the cause is almost always a mismatch between how the token was signed or validated and how the server expects it. This article gives you five concrete checks to isolate the mismatch, then explains the underlying mechanics so you can prevent it from happening again.

Check 1: Verify the Signing Algorithm

The most common mismatch is an algorithm confusion between HS256 (symmetric, single secret) and RS256 (asymmetric, public/private key pair). If the token was signed with RS256 but the server is configured to validate with HS256, or vice versa, every request will fail with a 401. In production, check the alg header of the JWT (the first part, base64-decoded) and compare it to the server’s expected algorithm. Many JWT libraries allow you to explicitly whitelist algorithms; if none is set, they may default to a permissive mode that accepts both, which is a security risk. Always set the exact algorithm on both the signing and verification side.

Check 2: Compare the Issuer and Audience Claims

The iss (issuer) and aud (audience) claims are often checked by the server. If the token was issued by an authentication service with iss: https://auth.example.com but the API expects iss: https://api.example.com, the token is rejected. Similarly, the aud claim must match the audience the API expects. This mismatch frequently appears when you have multiple services sharing the same JWT secret or key pair. Use a tool like jwt.io to decode the token and inspect these claims, then verify them against your server’s configuration.

Check 3: Check the Clock Skew and Expiry

JWT validation includes exp (expiration) and sometimes nbf (not before) claims. If the server’s clock is ahead of the token issuer’s clock by more than the allowed skew (often 30-60 seconds), a token that is still valid will appear expired. In production, ensure all servers use NTP to synchronize their clocks. Also check if the token has a very short expiry (e.g., 5 minutes) and the client is caching it beyond that. A simple fix is to increase the allowed clock skew in the validation options, but only if the time difference is small.

Check 4: Verify the Secret or Public Key

If the algorithm is correct and the claims are fine, the next suspect is the key. For HS256, the server must have the exact same secret string (or its base64-decoded bytes) that was used to sign. For RS256, the server must have the correct public key that corresponds to the private key used for signing. A common production mistake is having a different secret in the environment variable on the API server than on the token issuer, or having a trailing newline or space in the secret. Double-check the key material by generating a test token with the same key and trying to validate it locally.

Check 5: Inspect the Token for Tampering

If the token is malformed or has been tampered with, the signature will not match. In production, this can happen if a proxy or load balancer truncates the token, or if the client sends the token with extra whitespace or quotes. Also, some frameworks expect the token in the Authorization header as Bearer <token>; if the scheme is missing or misspelled, the server may reject it. Use a debugging tool to log the exact header received and compare it to what the client sent. If the token is valid when tested locally but fails in production, the issue is often in the transport layer.

Background: How JWT Authentication Works

JSON Web Tokens (JWT) are a compact, URL-safe way to represent claims between two parties. A JWT consists of three parts: a header, a payload, and a signature. The header specifies the signing algorithm, the payload contains the claims (like sub, exp, iss, aud), and the signature is computed over the header and payload using a secret (HS256) or a private key (RS256). When a client sends a request with a JWT, the server decodes the token, verifies the signature, and checks the claims. If any of these steps fail, the server returns a 401 Unauthorized. The mismatch can be in the algorithm, the key, the claims, or the time.

Common Problems and Misconceptions

  • Misconception: JWT is encrypted. JWT is signed, not encrypted. The payload is base64-encoded, so anyone can read it. Do not put sensitive data in a JWT without additional encryption.
  • Problem: Using the wrong key type. For RS256, you must use the public key for verification, not the private key. Some libraries will accept the private key, but it is a security risk.
  • Problem: Ignoring the kid header. If the token has a kid (key ID) header, the server should use it to select the correct key from a set. If the server ignores it and uses a default key, the signature may fail.
  • Problem: Base64 URL vs standard Base64. JWT uses base64url encoding, which replaces + and / with - and _. If a library decodes with standard base64, the token will be corrupted.

How to Diagnose the Mismatch

Start by capturing the exact token from the failing request. Use browser developer tools or server logs to get the Authorization header. Then decode the token manually or with a tool like jwt.io. Check the header and payload. Next, reproduce the validation locally using the same library and configuration as your production server. If it validates locally, the issue is in the environment (key, clock, or proxy). If it fails locally, you can step through the validation logic to see which check fails. Many JWT libraries provide detailed error messages that tell you exactly why the token is invalid, such as “signature verification failed” or “token expired”.

Alternatives to JWT for API Authentication

While JWT is popular for stateless authentication, it is not the only option. OAuth2 with opaque tokens (random strings stored server-side) is an alternative that is easier to revoke. Session cookies with a server-side session store are another option, especially for web applications. These alternatives avoid the mismatch problem because the server does not need to validate a signature; it just looks up the token in a database. However, they may require more server-side state and are not as scalable for distributed systems. Choose JWT when you need statelessness and are willing to handle key management carefully.

Frequently Asked Questions

Why does my JWT work in development but fail in production?

Most often it is a difference in configuration: a different secret, a different clock, or a different expected issuer/audience. Check your environment variables and the server’s time settings. Also, ensure the token is not being altered by a proxy.

What does “signature verification failed” mean?

It means the server computed the signature from the header and payload using the configured key and it did not match the signature in the token. This happens when the key is wrong or the token has been modified after signing.

How do I fix a clock skew issue?

Set the allowed clock skew in your JWT validation options, usually 30 seconds to a few minutes. Also, synchronize all servers with NTP to minimize the skew.

Can I use the same JWT for multiple APIs?

Yes, if all APIs share the same key and the token’s aud claim includes all of them, or if the APIs do not check aud. However, this increases the risk if one API is compromised. It is better to issue separate tokens per audience.

Is it safe to use HS256 in production?

HS256 is safe if the secret is strong and kept secret. The risk is that any party with the secret can both sign and verify tokens, so it must not be shared with clients. For multi-service environments, RS256 is preferred because the private key stays with the issuer.

What if the token is expired but the client keeps sending it?

The server will return a 401. The client should detect this and request a new token via a refresh token or re-authentication. Do not increase the expiry time to avoid the issue; that weakens security.

Related

Method: the standard formula for this calculation, rounded as each result states. See how the calculators work or report an error.