PyJWT 用 jwt.encode() 和 jwt.decode() 编码和解码 JSON Web 令牌,并用 PyJWKClient 从 JWKS 端点获取签名密钥。非对称算法由可选依赖 crypto 提供,它会引入 pyca/cryptography;装上它后,2.15.1 支持 HS、RS、PS 和 ES 系列以及 ES256K 和 EdDSA,但不支持较新的 Ed25519 和 Ed448 名称,使用它们会抛出 NotImplementedError: Algorithm not supported。
它的验证默认设置很严格。不传 algorithms 调用 jwt.decode() 会报错 It is required that you pass in a value for the "algorithms" argument;未签名的 alg: none 令牌从未验证通过——即使传入 algorithms=["none"] 也不行;用作 HS256 密钥的 PEM 或 OpenSSH 公钥被拒绝,报错 InvalidKeyError。ES256 与 P-256 绑定:用 P-384 密钥签名时因曲线不匹配而失败。
留给你处理的部分:exp 是可选的,因此除非在 options 参数的 require 中列出它,否则不含它的令牌永远都能解码;leeway 默认为零,因此时钟相差几秒的服务器就会对是否过期产生分歧。过短的 HMAC 密钥也会被接受,只给出一条 InsecureKeyLengthWarning,在日志中很容易被忽略——可以用 JWT 密钥检测工具测试密钥。
ES256 签名是 JWS 要求的 64 字节原始 r‖s 形式;签名被拼装成 DER 的令牌——例如来自 KMS 签名调用——会报出笼统的 Signature verification failed。把令牌粘贴到 JWT 调试器中查看签名长度,再用 DER ⇄ 原始格式转换器转换。
示例锁定了算法、颁发者和受众,要求 exp,并允许 30 秒的时钟漂移——有了这四项设置,才能放心地对其他服务签发的令牌调用 jwt.decode()。