python-jose: JOSE Implementation for Python
raw JSON → 3.5.0 verified Tue May 12 auth: no python install: verified quickstart: verified
python-jose is an active Python library implementing the JSON Object Signing and Encryption (JOSE) standards, including JSON Web Signature (JWS), JSON Web Encryption (JWE), JSON Web Key (JWK), JSON Web Algorithms (JWA), and JSON Web Tokens (JWT). Currently at version 3.5.0, it maintains a regular release schedule with significant updates to Python version support and cryptographic backends.
pip install python-jose Common errors
error jose.exceptions.JWSError: Signature verification failed ↓
cause The token's signature does not match the signature generated using the provided key and algorithm, indicating tampering, an incorrect key, or an invalid token.
fix
Ensure the correct secret key (or public key for asymmetric algorithms) is provided to
jose.jwt.decode, and that the token is valid and untampered. error ValueError: The token's alg header value 'HS256' does not match the provided allowed algorithms. ↓
cause The algorithm specified in the JWT header (`alg`) is not present in the list of algorithms explicitly allowed during the decoding process.
fix
When decoding, explicitly pass the token's algorithm in the
algorithms list: jose.jwt.decode(token, key, algorithms=['HS256']). error ImportError: You must install the 'cryptography' backend to use this algorithm. ↓
cause The `cryptography` library, which provides the necessary cryptographic primitives for certain algorithms (e.g., RS256, ES256), is not installed as an optional dependency.
fix
Install the necessary backend for
python-jose: pip install "python-jose[cryptography]". error ModuleNotFoundError: No module named 'jose' ↓
cause The `python-jose` library has not been installed, or the Python environment where the code is executed does not have access to the installed library.
fix
Install the library using pip:
pip install python-jose. Warnings
breaking Python 3.8 support was removed in version 3.5.0. Prior versions also removed support for Python 3.6/3.7 (v3.4.0) and 2.7/3.5 (v3.3.0). ↓
fix Upgrade to a supported Python version (3.9+ for python-jose 3.5.0).
gotcha The default cryptographic backend for `python-jose` has changed across versions (PyCryptodome in 2.0.0, native Python `rsa` in 3.0.0). Since 3.3.0, while native backends (rsa/ecdsa) are always installed, `pyca/cryptography` is the recommended backend for performance and security. Not installing with `pip install python-jose[cryptography]` can lead to slower native Python implementations being used by default. ↓
fix Always install with `pip install python-jose[cryptography]` for production environments to ensure optimal performance and security. Review your installed dependencies to confirm `cryptography` is active.
breaking Versions prior to 3.4.0 were vulnerable to Improper Handling of Highly Compressed Data (CVE-2024-33664, JWE size limit) and Improper Verification of Cryptographic Signature (CVE-2024-33663, signing JWT with public key forbidden). ↓
fix Upgrade to `python-jose` version 3.4.0 or higher immediately to patch critical security vulnerabilities.
deprecated The usage of `datetime.utcnow()` was replaced with `datetime.now(UTC)` in version 3.4.0 due to `utcnow()` being deprecated in Python 3.11. Code relying on `utcnow()` with older versions might encounter deprecation warnings. ↓
fix Upgrade to `python-jose` 3.4.0+ to avoid `datetime.utcnow()` deprecation warnings and ensure future compatibility.
gotcha Version 3.5.0 removed `get_random_bytes` from the `cryptography` backend and removed sensitive information from `JWKError` exceptions. If your code directly accessed `get_random_bytes` through the backend or relied on specific error message content from `JWKError`, this might be a breaking change. ↓
fix Review code for direct access to backend-specific utilities like `get_random_bytes` or reliance on `JWKError` message specifics. Adapt to the new behavior or use standard `os.urandom` if random bytes are needed.
gotcha Some external resources suggest `python-jose` might be less actively maintained compared to alternatives like `PyJWT` or `joserfc` and recommend considering these for new projects or migrations. While `python-jose` still receives updates, this feedback indicates a potential concern for long-term support or advanced features. ↓
fix Evaluate your project's specific needs for JOSE implementation. If long-term maintenance, broader community support, or specific advanced features are critical, consider alternatives like `PyJWT` or `joserfc` (from Authlib), which may offer different API structures.
Install
pip install python-jose[cryptography] Install compatibility verified last tested: 2026-05-12
python os / libc variant status wheel install import disk
3.10 alpine (musl) python-jose wheel - 0.12s 20.5M
3.10 alpine (musl) cryptography wheel - 0.30s 37.0M
3.10 alpine (musl) python-jose - - 0.11s 20.5M
3.10 alpine (musl) cryptography - - 0.30s 36.0M
3.10 slim (glibc) python-jose wheel 1.8s 0.09s 21M
3.10 slim (glibc) cryptography wheel 2.9s 0.22s 37M
3.10 slim (glibc) python-jose - - 0.08s 21M
3.10 slim (glibc) cryptography - - 0.20s 36M
3.11 alpine (musl) python-jose wheel - 0.18s 22.9M
3.11 alpine (musl) cryptography wheel - 0.53s 39.7M
3.11 alpine (musl) python-jose - - 0.19s 22.9M
3.11 alpine (musl) cryptography - - 0.62s 38.6M
3.11 slim (glibc) python-jose wheel 1.9s 0.15s 23M
3.11 slim (glibc) cryptography wheel 2.9s 0.48s 40M
3.11 slim (glibc) python-jose - - 0.15s 23M
3.11 slim (glibc) cryptography - - 0.49s 39M
3.12 alpine (musl) python-jose wheel - 0.15s 14.6M
3.12 alpine (musl) cryptography wheel - 0.40s 31.3M
3.12 alpine (musl) python-jose - - 0.15s 14.6M
3.12 alpine (musl) cryptography - - 0.43s 30.3M
3.12 slim (glibc) python-jose wheel 1.8s 0.15s 15M
3.12 slim (glibc) cryptography wheel 2.4s 0.44s 32M
3.12 slim (glibc) python-jose - - 0.15s 15M
3.12 slim (glibc) cryptography - - 0.46s 31M
3.13 alpine (musl) python-jose wheel - 0.16s 14.4M
3.13 alpine (musl) cryptography wheel - 0.37s 31.1M
3.13 alpine (musl) python-jose - - 0.14s 14.3M
3.13 alpine (musl) cryptography - - 0.39s 29.9M
3.13 slim (glibc) python-jose wheel 1.9s 0.14s 15M
3.13 slim (glibc) cryptography wheel 2.6s 0.40s 32M
3.13 slim (glibc) python-jose - - 0.15s 15M
3.13 slim (glibc) cryptography - - 0.42s 30M
3.9 alpine (musl) python-jose wheel - 0.11s 20.0M
3.9 alpine (musl) cryptography wheel - 0.28s 37.3M
3.9 alpine (musl) python-jose - - 0.11s 20.0M
3.9 alpine (musl) cryptography - - 0.29s 36.2M
3.9 slim (glibc) python-jose wheel 2.2s 0.12s 20M
3.9 slim (glibc) cryptography wheel 3.4s 0.29s 38M
3.9 slim (glibc) python-jose - - 0.10s 20M
3.9 slim (glibc) cryptography - - 0.26s 37M
Imports
- jwt
from jose import jwt - jws
from jose import jws - jwe
from jose import jwe - jwk
from jose import jwk
Quickstart verified last tested: 2026-04-24
import os
from jose import jwt
# IMPORTANT: Use a strong, securely generated secret key in production
SECRET_KEY = os.environ.get('JWT_SECRET_KEY', 'your-super-secret-key-please-change-me')
ALGORITHM = "HS256"
# 1. Encode a JWT
payload = {"user_id": "123", "username": "testuser", "role": "admin"}
encoded_jwt = jwt.encode(payload, SECRET_KEY, algorithm=ALGORITHM)
print(f"Encoded JWT: {encoded_jwt}")
# 2. Decode and verify a JWT
try:
decoded_payload = jwt.decode(encoded_jwt, SECRET_KEY, algorithms=[ALGORITHM])
print(f"Decoded Payload: {decoded_payload}")
except Exception as e:
print(f"Error decoding JWT: {e}")