JWT Parsed Without Signature Verification

HIGH

jwt.ParseUnverified() skips signature validation entirely — any attacker can forge arbitrary JWT claims (sub, role, admin) without knowing the signing key.

Rule Information

Language
Go
Category
Security
Author
Shivasurya
Shivasurya
Last Updated
2026-04-13
Tags
gosecurityjwtparse-unverifiedauthentication-bypassCWE-345CWE-347OWASP-A08
CWE References

Interactive Playground

Experiment with the vulnerable code and security rule below. Edit the code to see how the rule detects different vulnerability patterns.

pathfinder scan --ruleset golang/GO-JWT-002 --project .
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
rule.py
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
Cross-file analysis: 3 files

About This Rule

Understanding the vulnerability and how it is detected

JWT (JSON Web Token) security depends entirely on signature verification — the signature proves the token was issued by a party holding the signing key and has not been tampered with. `jwt.ParseUnverified()` in the golang-jwt/jwt library parses the token and decodes its claims but **explicitly skips all signature validation**.

A JWT consists of three base64url-encoded sections: header.payload.signature. Any client can construct a JWT with arbitrary claims in the payload (role: "admin", sub: "other_user", etc.) and sign it with any key or omit the signature entirely. Without signature verification, the server has no way to distinguish forged tokens from legitimately issued ones.

**CVE-2020-26160** (dgrijalva/jwt-go, the predecessor to golang-jwt/jwt): This CVE exposed another signature verification bypass — the `aud` (audience) claim was not validated when not explicitly required, allowing tokens intended for one service to be accepted by another. This demonstrates how JWT validation failures require attention to the complete set of standard claims, not just the signature.

**CVE-2024-51744** (golang-jwt/jwt v5 < 5.2.2): Improper handling of newlines in multi-line RSA/ECDSA key blocks allowed crafted keys to bypass signature verification in certain configurations. Fixed in v5.2.2.

**RFC 8725 — "JSON Web Token Best Current Practices"** (published 2020) explicitly recommends: - Always perform algorithm validation against an allowlist - "Reject tokens with `\"alg\": \"none\"`" - Validate all claims (iss, sub, aud, exp, nbf, iat) - Use only one key per algorithm family

**When ParseUnverified() is legitimate**: Extracting the issuer (`iss`) claim from an unverified token to look up the correct validation key (JWKS endpoint selection). The token MUST then be re-validated using jwt.Parse() with the retrieved key.

Security Implications

Potential attack scenarios if this vulnerability is exploited

1

Complete Authentication Bypass

An attacker creates a JWT with admin claims (`"role":"admin"`, `"is_admin":true`, `"sub":"admin_user_id"`) and any signature (or no signature). ParseUnverified() accepts this token, granting the attacker full administrative access.

2

Horizontal Privilege Escalation

Changing the `sub` (subject) claim to another user's ID impersonates that user. Without signature verification, every authenticated account is accessible by any other authenticated user.

3

JWT Algorithm Confusion

If the server accepts `"alg": "none"` tokens (a related vulnerability), the attacker removes the signature entirely. Combining ParseUnverified with algorithm confusion creates a completely bypassed authentication system.

How to Fix

Recommended remediation steps

  • 1Use jwt.Parse() or jwt.ParseWithClaims() with an explicit key validation function.
  • 2In the key validation function, check t.Method against the expected signing method type.
  • 3Validate all standard claims: iss, aud, exp, nbf, iat using jwt.With* options.
  • 4Explicitly reject tokens with alg=none in the key validation function.
  • 5Keep golang-jwt/jwt updated — CVE-2024-51744 was fixed in v5.2.2.
  • 6Store JWT secrets in environment variables or secrets managers, never in source code.
  • 7Set short token expiration times (15 minutes for access tokens) to limit window of forged tokens.

Detection Scope

How Code Pathfinder analyzes your code for this vulnerability

Detects all calls to ParseUnverified() from golang-jwt/jwt packages. Flags any use regardless of context — legitimate use requires a follow-up jwt.Parse() which this rule assumes is missing until proven otherwise.

Compliance & Standards

Industry frameworks and regulations that require detection of this vulnerability

OWASP Top 10
A08:2021 — Software and Data Integrity Failures; A07:2021 — Authentication Failures
RFC 8725
JSON Web Token Best Current Practices: validate algorithm, validate all claims, use appropriate key lengths, reject alg=none. URL: https://www.rfc-editor.org/rfc/rfc8725
CWE Top 25 (2024)
CWE-347 — Improper Verification of Cryptographic Signature
PCI DSS v4.0
Requirement 8.3 — Authentication factor security

References

External resources and documentation

Similar Rules

Explore related security rules for Go

Frequently Asked Questions

Common questions about JWT Parsed Without Signature Verification

JWT (JSON Web Token) security depends entirely on signature verification — the signature proves the token was issued by a party holding the signing key and has not been tampered with. `jwt.ParseUnverified()` in the golang-jwt/jwt library parses the token and decodes its claims but **explicitly skips all signature validation**. A JWT consists of three base64url-encoded sections: header.payload.signature. Any client can construct a JWT with arbitrary claims in the payload (role: "admin", sub: "other_user", etc.) and sign it with any key or omit the signature entirely. Without signature verification, the server has no way to distinguish forged tokens from legitimately issued ones. **CVE-2020-26160** (dgrijalva/jwt-go, the predecessor to golang-jwt/jwt): This CVE exposed another signature verification bypass — the `aud` (audience) claim was not validated when not explicitly required, allowing tokens intended for one service to be accepted by another. This demonstrates how JWT validation failures require attention to the complete set of standard claims, not just the signature. **CVE-2024-51744** (golang-jwt/jwt v5 < 5.2.2): Improper handling of newlines in multi-line RSA/ECDSA key blocks allowed crafted keys to bypass signature verification in certain configurations. Fixed in v5.2.2. **RFC 8725 — "JSON Web Token Best Current Practices"** (published 2020) explicitly recommends: - Always perform algorithm validation against an allowlist - "Reject tokens with `\"alg\": \"none\"`" - Validate all claims (iss, sub, aud, exp, nbf, iat) - Use only one key per algorithm family **When ParseUnverified() is legitimate**: Extracting the issuer (`iss`) claim from an unverified token to look up the correct validation key (JWKS endpoint selection). The token MUST then be re-validated using jwt.Parse() with the retrieved key.
Use Code Pathfinder to scan your codebase: pathfinder scan --ruleset golang/GO-JWT-002 --project .
This vulnerability is rated as HIGH severity.
Yes! Code Pathfinder allows you to customize rules. Modify detection patterns, adjust severity levels, add custom sanitizers, and configure the rule to fit your organization's security policies.

New feature

Get these findings posted directly on your GitHub pull requests

The JWT Parsed Without Signature Verification rule runs in CI and posts inline review comments on the exact lines — no dashboard, no SARIF viewer.

See how it works