jwt-validate

Compare original and translation side by side

🇺🇸

Original

English
🇨🇳

Translation

Chinese

JWT Validate

JWT验证

Verify a JWT's signature and validate its claims. Confirms the token is authentic, unexpired, and structurally sound.
验证JWT的签名并校验其声明,确认令牌真实可信、未过期且结构合规。

Validation Order

校验顺序

Check in this order. Stop and report at the first failure.
按以下顺序校验,遇到第一个失败项就停止并返回结果。

1. Structure

1. 结构

  • Exactly 3 dot-separated parts, each valid base64url
  • Header and payload parse as valid JSON
  • Header contains
    alg
    ;
    alg
    is not
    none
    (unless explicitly expected)
  • 恰好包含3个点号分隔的部分,每个部分都是合法的base64url格式
  • 头部和载荷可解析为合法JSON
  • 头部包含
    alg
    字段;
    alg
    值不为
    none
    (除非明确预期允许该值)

2. Claims

2. 声明

  • exp
    must be in the future (report time until expiry or how long ago it expired)
  • nbf
    must be in the past or present
  • iat
    must be in the past; flag if > 30 days old
  • iss
    ,
    aud
    ,
    sub
    — if user provides expected values, they must match
  • Allow 60 seconds clock skew tolerance on all time checks
  • exp
    必须为未来时间(报告距离过期的剩余时间或已过期时长)
  • nbf
    必须为过去或当前时间
  • iat
    必须为过去时间;如果超过30天需要标记
  • iss
    aud
    sub
    — 如果用户提供了预期值,必须完全匹配
  • 所有时间检查允许60秒的时钟偏移容差

3. Signature

3. 签名

Requires the user to provide a secret, PEM public key, or JWKS URI. Always pass secrets and tokens via inline env vars to avoid shell history exposure.
Node.js (preferred):
First, ensure
jose
is available — install it globally if missing:
bash
node --input-type=module -e "await import('jose')" 2>/dev/null || npm install -g jose
Then verify the token:
bash
JWT_TOKEN='the.jwt.here' JWT_SECRET='user-provided-secret' node --input-type=module -e "import {jwtVerify} from 'jose'; try { const {payload}=await jwtVerify(process.env.JWT_TOKEN, new TextEncoder().encode(process.env.JWT_SECRET), {algorithms:['HS256'],clockTolerance:60}); console.log('VALID'); console.log(JSON.stringify(payload,null,2)); } catch(e) { console.log('INVALID:',e.message); }"
Python:
bash
JWT_TOKEN='the.jwt.here' JWT_SECRET='user-provided-secret' python3 -c "
import jwt,json,os
try:
  d=jwt.decode(os.environ['JWT_TOKEN'],os.environ['JWT_SECRET'],algorithms=['HS256'],leeway=60)
  print('VALID'); print(json.dumps(d,indent=2))
except Exception as e: print(f'INVALID: {e}')
"
JWKS verification (Node.js):
bash
JWT_TOKEN='the.jwt.here' JWKS_URI='https://example.auth0.com/.well-known/jwks.json' node --input-type=module -e "import {jwtVerify,createRemoteJWKSet} from 'jose'; try { const {payload}=await jwtVerify(process.env.JWT_TOKEN, createRemoteJWKSet(new URL(process.env.JWKS_URI)), {algorithms:['RS256']}); console.log('VALID'); console.log(JSON.stringify(payload,null,2)); } catch(e) { console.log('INVALID:',e.message); }"
If no secret/key is provided, perform structure + claims validation only, and clearly state the signature was NOT verified.
需要用户提供密钥、PEM公钥或JWKS URI。请始终通过内联环境变量传递密钥和令牌,避免泄露shell历史记录。
Node.js(首选):
首先,确保
jose
已安装,若缺失则全局安装:
bash
node --input-type=module -e "await import('jose')" 2>/dev/null || npm install -g jose
然后验证令牌:
bash
JWT_TOKEN='the.jwt.here' JWT_SECRET='user-provided-secret' node --input-type=module -e "import {jwtVerify} from 'jose'; try { const {payload}=await jwtVerify(process.env.JWT_TOKEN, new TextEncoder().encode(process.env.JWT_SECRET), {algorithms:['HS256'],clockTolerance:60}); console.log('VALID'); console.log(JSON.stringify(payload,null,2)); } catch(e) { console.log('INVALID:',e.message); }"
Python:
bash
JWT_TOKEN='the.jwt.here' JWT_SECRET='user-provided-secret' python3 -c "
import jwt,json,os
try:
  d=jwt.decode(os.environ['JWT_TOKEN'],os.environ['JWT_SECRET'],algorithms=['HS256'],leeway=60)
  print('VALID'); print(json.dumps(d,indent=2))
except Exception as e: print(f'INVALID: {e}')
"
JWKS校验 (Node.js):
bash
JWT_TOKEN='the.jwt.here' JWKS_URI='https://example.auth0.com/.well-known/jwks.json' node --input-type=module -e "import {jwtVerify,createRemoteJWKSet} from 'jose'; try { const {payload}=await jwtVerify(process.env.JWT_TOKEN, createRemoteJWKSet(new URL(process.env.JWKS_URI)), {algorithms:['RS256']}); console.log('VALID'); console.log(JSON.stringify(payload,null,2)); } catch(e) { console.log('INVALID:',e.message); }"
如果未提供密钥/公钥,仅执行结构+声明校验,并明确说明签名未被核验。

Output Format

输出格式

undefined
undefined

JWT Validation Report

JWT Validation Report

Structure: PASS Claims: PASS — exp 2025-06-15T12:00:00Z (expires in 2h) Signature: PASS — RS256, key kid "abc123" Result: VALID

On failure:
Structure: PASS Claims: PASS — exp 2025-06-15T12:00:00Z (expires in 2h) Signature: PASS — RS256, key kid "abc123" Result: VALID

校验失败时:

JWT Validation Report

JWT Validation Report

Structure: PASS Claims: FAIL — exp 2024-01-15T12:00:00Z (expired 6 months ago) Signature: SKIPPED Result: INVALID — token expired
undefined
Structure: PASS Claims: FAIL — exp 2024-01-15T12:00:00Z (expired 6 months ago) Signature: SKIPPED Result: INVALID — token expired
undefined

Security Rules

安全规则

  • Never trust the token's
    alg
    header for verification.
    Always use the algorithm the user expects or that matches the provided key type. Trusting the header enables algorithm confusion attacks where an attacker switches RS256 to HS256 and signs with the public key as an HMAC secret.
  • Always specify
    algorithms
    as an explicit allowlist
    in verification calls. Never pass
    algorithms: [decoded.header.alg]
    .
  • Never pass secrets/tokens as literal command-line arguments. Use environment variables. Args are visible in shell history and
    ps
    output.
  • alg: none
    — Flag as a critical security issue. The token is unsigned and cannot be trusted.
  • If no key is provided, validate structure and claims only. Clearly state: "Signature was NOT verified — token authenticity is unknown."

  • 绝对不要信任令牌的
    alg
    头来做校验。
    始终使用用户预期的算法,或与提供的密钥类型匹配的算法。信任该头部会导致算法混淆攻击,攻击者可将RS256切换为HS256,并用公钥作为HMAC密钥签名。
  • 始终在校验调用中将
    algorithms
    指定为明确的允许列表
    ,绝对不要传入
    algorithms: [decoded.header.alg]
  • 绝对不要将密钥/令牌作为字面量命令行参数传递。 请使用环境变量。参数会在shell历史和
    ps
    输出中可见。
  • alg: none
    — 标记为严重安全问题。该令牌未签名,不可信任。
  • 如果未提供密钥,仅校验结构和声明。明确说明: "Signature was NOT verified — token authenticity is unknown."