diff --git a/lib/jwt/__init__.py b/lib/jwt/__init__.py index 0631c99c..3208c39f 100644 --- a/lib/jwt/__init__.py +++ b/lib/jwt/__init__.py @@ -25,7 +25,7 @@ from .exceptions import ( ) from .jwks_client import PyJWKClient -__version__ = "2.2.0" +__version__ = "2.3.0" __title__ = "PyJWT" __description__ = "JSON Web Token implementation in Python" diff --git a/lib/jwt/api_jws.py b/lib/jwt/api_jws.py index a61d2277..f85072e0 100644 --- a/lib/jwt/api_jws.py +++ b/lib/jwt/api_jws.py @@ -113,14 +113,14 @@ class PyJWS: key = alg_obj.prepare_key(key) signature = alg_obj.sign(signing_input, key) - except KeyError: + except KeyError as e: if not has_crypto and algorithm in requires_cryptography: raise NotImplementedError( "Algorithm '%s' could not be found. Do you have cryptography " "installed?" % algorithm - ) + ) from e else: - raise NotImplementedError("Algorithm not supported") + raise NotImplementedError("Algorithm not supported") from e segments.append(base64url_encode(signature)) @@ -134,6 +134,7 @@ class PyJWS: key: str = "", algorithms: List[str] = None, options: Dict = None, + **kwargs, ) -> Dict[str, Any]: if options is None: options = {} @@ -162,8 +163,9 @@ class PyJWS: key: str = "", algorithms: List[str] = None, options: Dict = None, + **kwargs, ) -> str: - decoded = self.decode_complete(jwt, key, algorithms, options) + decoded = self.decode_complete(jwt, key, algorithms, options, **kwargs) return decoded["payload"] def get_unverified_header(self, jwt): @@ -236,8 +238,8 @@ class PyJWS: if not alg_obj.verify(signing_input, key, signature): raise InvalidSignatureError("Signature verification failed") - except KeyError: - raise InvalidAlgorithmError("Algorithm not supported") + except KeyError as e: + raise InvalidAlgorithmError("Algorithm not supported") from e def _validate_headers(self, headers): if "kid" in headers: diff --git a/lib/jwt/api_jwt.py b/lib/jwt/api_jwt.py index 7e21b754..f3b55d36 100644 --- a/lib/jwt/api_jwt.py +++ b/lib/jwt/api_jwt.py @@ -68,9 +68,7 @@ class PyJWT: key: str = "", algorithms: List[str] = None, options: Dict = None, - audience: Optional[Union[str, List[str]]] = None, - issuer: Optional[str] = None, - leeway: Union[float, timedelta] = 0, + **kwargs, ) -> Dict[str, Any]: if options is None: options = {"verify_signature": True} @@ -94,6 +92,7 @@ class PyJWT: key=key, algorithms=algorithms, options=options, + **kwargs, ) try: @@ -104,7 +103,7 @@ class PyJWT: raise DecodeError("Invalid payload string: must be a json object") merged_options = {**self.options, **options} - self._validate_claims(payload, merged_options, audience, issuer, leeway) + self._validate_claims(payload, merged_options, **kwargs) decoded["payload"] = payload return decoded @@ -115,20 +114,18 @@ class PyJWT: key: str = "", algorithms: List[str] = None, options: Dict = None, - audience: Optional[Union[str, List[str]]] = None, - issuer: Optional[str] = None, - leeway: Union[float, timedelta] = 0, + **kwargs, ) -> Dict[str, Any]: - decoded = self.decode_complete( - jwt, key, algorithms, options, audience, issuer, leeway - ) + decoded = self.decode_complete(jwt, key, algorithms, options, **kwargs) return decoded["payload"] - def _validate_claims(self, payload, options, audience, issuer, leeway): + def _validate_claims( + self, payload, options, audience=None, issuer=None, leeway=0, **kwargs + ): if isinstance(leeway, timedelta): leeway = leeway.total_seconds() - if not isinstance(audience, (str, type(None), Iterable)): + if not isinstance(audience, (bytes, str, type(None), Iterable)): raise TypeError("audience must be a string, iterable, or None") self._validate_required_claims(payload, options)