Mensaje de error
The specified alg value is not allowed
También se muestra como
- jwt.exceptions.InvalidAlgorithmError: The specified alg value is not allowed
PyJWT (Python) — jwt.exceptions.InvalidAlgorithmError
Qué significa
El `alg` del encabezado del token no está en la lista `algorithms` que pasas a `jwt.decode()`. PyJWT lo comprueba antes de verificar la firma, porque el encabezado lo elige quien generó el token y no debe decidir cómo se verifica. Puede que el token esté bien firmado, solo que con un algoritmo que no permites.
Por qué ocurre
El emisor cambió de algoritmo
frecuenteUna migración del proveedor de RS256 a ES256 (o la incorporación de una clave EdDSA) rompe los verificadores que fijan el valor antiguo. Los fallos empiezan justo con el despliegue y solo afectan a los tokens recién emitidos.
La JWK fija otro algoritmo
ocasionalCuando pasas una `PyJWK` (por ejemplo, de `PyJWKClient`), su `alg` también restringe la verificación. Una JWK etiquetada como RS256 no puede verificar un token ES256.
Un token que viene de otro sitio
ocasionalTokens de otro emisor, un token HS256 interno enviado a una API pública o un sondeo con `alg: "none"` o `HS256` contra una API protegida con RSA. En esos casos, el rechazo es correcto.
Cómo solucionarlo
- 1.
Leer primero el encabezado
`jwt.get_unverified_header()` muestra `alg` y `kid` sin confiar en nada. Compáralos con tu lista de permitidos y con las claves que publica tu emisor.
python print(jwt.get_unverified_header(token)) # {'alg': 'ES256', 'kid': '...', 'typ': 'JWT'} - 2.
Permitir exactamente el algoritmo del emisor
Pon en `algorithms` el algoritmo que usa tu emisor y resuelve las claves a partir de su JWKS. Durante una migración, incluye ambos algoritmos, cada uno asociado a su propia clave mediante `kid`.
python from jwt import PyJWKClient jwks = PyJWKClient("https://issuer.example.com/.well-known/jwks.json") signing_key = jwks.get_signing_key_from_jwt(token) claims = jwt.decode( token, signing_key.key, algorithms=["ES256"], # the algorithm(s) your issuer actually uses, never the token's own header audience="https://api.example.com", )