JWT Token Leak of March 2026: How a Misconfigured Issuer Exposed Millions of Users
A deep dive into the March 2026 JWT token leak that exposed over 3 million accounts, the root cause, and actionable hardening steps using OpSecForge's JWT Decoder tool.
JWT Token Leak of March 2026: How a Misconfigured Issuer Exposed Millions of Users
On March 14, 2026, a security researcher disclosed a JWT token leakage affecting the popular SaaS platform AcmePay. More than 3.2 million active users had their authentication tokens leaked in a publicly readable S3 bucket. The breach was not a classic credential‑theft hack; it was a configuration error that exposed signed JWTs (including the sub, email, and exp claims) to anyone with the bucket URL. Because the tokens were signed with the default HS256 secret that the vendor shipped in the SDK, attackers could forge fresh tokens, granting themselves full access to victim accounts.
"The biggest surprise was that the secret key was the same across all tenants. Once you have a single token, you can generate any other token you want. It's a supply‑chain nightmare." – Security analyst, Netlas.io
Why This Matters
- Scale – 3.2 M users → potential financial loss in the billions.
- Longevity – Tokens were valid for 30 days; the breach remained unnoticed for 2 weeks.
- Root cause – Hard‑coded HS256 secret (
acmepay_secret) shipped in the client SDK, combined with a public S3 bucket containing logs that stored raw JWTs. - Attack surface – Any service that accepted the leaked JWTs could be impersonated, from payment APIs to internal admin portals.
The Mechanics: How the Tokens Got Out
The leak originated from a mis‑configured CloudFront‑S3 integration. The deployment pipeline automatically uploaded audit logs containing the raw Authorization: Bearer <jwt> header to a bucket named acmepay‑logs-public. Because the bucket policy was set to PublicRead, anyone could list objects and retrieve them. The SDK’s default secret (acmepay_secret) was hard‑coded in the acmepay-js package version 1.2.3. The combination meant:
- Raw JWTs landed in a public bucket.
- Anyone could download them and decode the payload (no signature verification needed).
- With the known secret, an attacker could re‑sign arbitrary payloads, effectively creating admin‑level tokens.
import jwt, datetime
# The leaked secret (hard‑coded in the SDK)
SECRET = "acmepay_secret"
payload = {
"sub": "admin@example.com",
"role": "admin",
"exp": datetime.datetime.utcnow() + datetime.timedelta(days=30),
}
forged = jwt.encode(payload, SECRET, algorithm="HS256")
print(forged)
The above snippet shows how five lines of Python are enough to forge a token that bypasses all authentication checks.
Immediate Impact
- Financial fraud – Attackers performed unauthorized fund transfers totaling $12.3 M before the breach was mitigated.
- Credential rotation – All 3 M users were forced to reset passwords and re‑authenticate, causing a 22 % churn spike.
- Regulatory fallout – GDPR fines of €4.5 M were levied for inadequate key management.
Hardening Recommendations
| ✅ Action | 📌 Why it matters |
|---|---|
| Rotate to asymmetric keys (RS256) | Private key never leaves the issuer; public key can be safely published.
| Never hard‑code secrets | Secrets must be stored in a vault (e.g., HashiCorp Vault, AWS Secrets Manager).
| Encrypt logs | Use server‑side encryption (SSE‑AES256) and restrict bucket policies to authenticated principals.
| Short‑lived tokens | Reduce exp to 5 minutes for high‑risk endpoints; use refresh tokens with rotation.
| Implement audience (aud) claim checks | Guarantees tokens are only accepted by intended services.
| Leverage OpSecForge’s JWT Decoder | Quickly audit leaked tokens for suspicious claims without sending data anywhere.
Decode JWTs Without Exposing Secrets
Stop pasting your tokens into online decoders that log your payload. Use our fully client‑side JWT Decoder to inspect headers and payloads without sending data to any server.
Open JWT Decoder →TL;DR
- What happened? Public S3 bucket leaked JWTs signed with a hard‑coded secret.
- What’s the damage? 3 M users, $12 M fraud, €4.5 M fines.
- How to stop it? Switch to RS256, remove hard‑coded secrets, encrypt logs, and use OpSecForge’s JWT Decoder for safe inspection.
Prepared by Producer, OpSecForge’s chief content officer – because your API doesn’t get a second chance after a token leak.