{"id":31859491,"url":"https://github.com/python-ellar/ellar-jwt","last_synced_at":"2025-10-12T15:26:00.247Z","repository":{"id":186984894,"uuid":"675842837","full_name":"python-ellar/ellar-jwt","owner":"python-ellar","description":"JWT Module for Ellar","archived":false,"fork":false,"pushed_at":"2025-10-04T13:44:11.000Z","size":163,"stargazers_count":1,"open_issues_count":1,"forks_count":0,"subscribers_count":1,"default_branch":"master","last_synced_at":"2025-10-07T16:38:08.936Z","etag":null,"topics":[],"latest_commit_sha":null,"homepage":null,"language":"Python","has_issues":true,"has_wiki":null,"has_pages":null,"mirror_url":null,"source_name":null,"license":"mit","status":null,"scm":"git","pull_requests_enabled":true,"icon_url":"https://github.com/python-ellar.png","metadata":{"files":{"readme":"README.md","changelog":null,"contributing":null,"funding":null,"license":"LICENSE","code_of_conduct":null,"threat_model":null,"audit":null,"citation":null,"codeowners":null,"security":null,"support":null,"governance":null,"roadmap":null,"authors":null,"dei":null,"publiccode":null,"codemeta":null}},"created_at":"2023-08-07T21:27:57.000Z","updated_at":"2025-10-04T08:48:01.000Z","dependencies_parsed_at":"2023-09-01T09:22:49.308Z","dependency_job_id":"8b8ba606-ca4c-4e82-ad6e-4eda707a55e9","html_url":"https://github.com/python-ellar/ellar-jwt","commit_stats":null,"previous_names":["eadwincode/ellar-jwt","python-ellar/ellar-jwt"],"tags_count":10,"template":false,"template_full_name":null,"purl":"pkg:github/python-ellar/ellar-jwt","repository_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/python-ellar%2Fellar-jwt","tags_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/python-ellar%2Fellar-jwt/tags","releases_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/python-ellar%2Fellar-jwt/releases","manifests_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/python-ellar%2Fellar-jwt/manifests","owner_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners/python-ellar","download_url":"https://codeload.github.com/python-ellar/ellar-jwt/tar.gz/refs/heads/master","sbom_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/python-ellar%2Fellar-jwt/sbom","scorecard":null,"host":{"name":"GitHub","url":"https://github.com","kind":"github","repositories_count":279011851,"owners_count":26085004,"icon_url":"https://github.com/github.png","version":null,"created_at":"2022-05-30T11:31:42.601Z","updated_at":"2022-07-04T15:15:14.044Z","status":"online","status_checked_at":"2025-10-12T02:00:06.719Z","response_time":53,"last_error":null,"robots_txt_status":"success","robots_txt_updated_at":"2025-07-24T06:49:26.215Z","robots_txt_url":"https://github.com/robots.txt","online":true,"can_crawl_api":true,"host_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub","repositories_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories","repository_names_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repository_names","owners_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners"}},"keywords":[],"created_at":"2025-10-12T15:25:56.822Z","updated_at":"2025-10-12T15:26:00.239Z","avatar_url":"https://github.com/python-ellar.png","language":"Python","funding_links":[],"categories":[],"sub_categories":[],"readme":"\u003cp align=\"center\"\u003e\n  \u003ca href=\"#\" target=\"blank\"\u003e\u003cimg src=\"https://python-ellar.github.io/ellar/img/EllarLogoB.png\" width=\"200\" alt=\"Ellar Logo\" /\u003e\u003c/a\u003e\n\u003c/p\u003e\n\n![Test](https://github.com/eadwinCode/ellar-jwt/actions/workflows/test_full.yml/badge.svg)\n![Coverage](https://img.shields.io/codecov/c/github/python-ellar/ellar-jwt)\n[![PyPI version](https://badge.fury.io/py/ellar-jwt.svg)](https://badge.fury.io/py/ellar-jwt)\n[![PyPI version](https://img.shields.io/pypi/v/ellar-jwt.svg)](https://pypi.python.org/pypi/ellar-jwt)\n[![PyPI version](https://img.shields.io/pypi/pyversions/ellar-jwt.svg)](https://pypi.python.org/pypi/ellar-jwt)\n\n\n## Introduction\nJWT utilities module for Ellar.\n\n\n## Installation\n```shell\n$(venv) pip install ellar-jwt\n```\n\n## Usage\n\nImport `JWTModule`:\n\n```python\nfrom ellar.common import Module\nfrom ellar_jwt import JWTModule\n\n\n@Module(\n    modules=[JWTModule.setup(signing_secret_key='my_private_key')]\n)\nclass AuthModule:\n    pass\n\n```\n\nInject `JWTService` where its needed as shown below\n\n```python\nfrom ellar_jwt import JWTService\nfrom ellar.di import injectable\n\n\n@injectable()\nclass AuthService:\n  def __init__(self, jwt_service: JWTService) -\u003e None:\n    self.jwt_service = jwt_service\n\n  async def sign_in(self, username: str, password: str) -\u003e t.Dict:\n      user = await self.user_service.find_one(username)\n      if user.password != credentials.password:\n          raise HTTPException(status_code=status.HTTP_403_FORBIDDEN)\n\n      return {\n          'access_token': await self.jwt_service.sign_async(user.dict())\n      }\n```\n\n## JWTModule Setup\nThere are two ways in config JWTModule\n- **setup**: \n\n  `JWTModule.setup` takes some parameters that allows instant configuration of the `JWTConfiguration` schema required by the `JWTService`\n    \n    For example:\n    ```python\n    from ellar.common import Module\n    from ellar_jwt import JWTModule\n    \n    \n    @Module(\n        modules=[JWTModule.setup(signing_secret_key='my_private_key', issuer='https://google.com')]\n    )\n    class AuthModule:\n        pass\n    ```\n- **register**:\n\n    `JWTModule.register` lets you provide JWT configuration in the Ellar application config object using the `JWT_CONFIG` key. \n    The register function will create a `ModuleSetup` object that will inject application `config` to a JWT config factory\n    \n    for example:\n    ```python\n    # config.py\n    import json\n    from datetime import timedelta\n    \n    class DevelopmentConfig:\n        JWT_CONFIG = {\n            'algorithm':\"HS256\", # allow_algorithms=[\"HS256\",\"HS384\",\"HS512\",\"RS256\",\"RS384\",\"RS512\",\"ES256\",\"ES384\",\"ES512\"]\n            'leeway': 0, # t.Union[float, int, timedelta]\n        \n            'signing_secret_key': 'secret', # secret or private key\n            'verifying_secret_key': \"\", # public key\n            'audience': None,\n        \n            'issuer': None,\n            'jwk_url': None,\n        \n            'jti': \"jti\",\n            'lifetime': timedelta(minutes=5), # token lifetime, this will example in 5 mins\n        \n            'json_encoder':json.JSONEncoder # token lifetime, this will be an example \n        }\n    ```\n    In `auth/module.py`\n    ```python\n    from ellar.common import Module\n    from ellar_jwt import JWTModule\n        \n        \n    @Module(\n        modules=[JWTModule.register_setup()]\n    )\n    class AuthModule:\n        pass\n    ```\n\n\n## JWT Configuration Options\n```python\nimport json\nfrom datetime import timedelta\n\n\nJWT_CONFIG = {\n    'algorithm':\"HS256\", # allow_algorithms=[\"HS256\",\"HS384\",\"HS512\",\"RS256\",\"RS384\",\"RS512\",\"ES256\",\"ES384\",\"ES512\"]\n    'leeway': 0, # t.Union[float, int, timedelta]\n\n    'signing_secret_key': 'secret', # secret or private key\n    'verifying_secret_key': \"\", # public key\n    'audience': None,\n\n    'issuer': None,\n    'jwk_url': None,\n\n    'jti': \"jti\",\n    'lifetime': timedelta(minutes=5), # token lifetime, this will example in 5 mins\n\n    'json_encoder':json.JSONEncoder # token lifetime, this will be an example \n}\n```\n\n- ### `lifetime`\nA `datetime.timedelta` object is employed to define the validity duration of the tokens. \nWhen generating a token, this `timedelta` value is combined with the present `UTC` time to establish the default `exp` claim value for the token.\n\n- ### `algorithm`\nThe chosen algorithm from the `PyJWT` library governs the signing and verification procedures for tokens. \nFor symmetric HMAC signing and verification, you have the option to use the following algorithms: `HS256`, `HS384`, and `HS512`. \nIn the case of an HMAC algorithm, the signing_secret_key serves both as the signing and verifying key, rendering the `verifying_secret_key` setting redundant.\nOn the other hand, for asymmetric RSA signing and verification, you can opt for the following algorithms: `RS256`, `RS384`, and `RS512`. \nIn this scenario, selecting an RSA algorithm mandates configuring the `signing_secret_key` setting with an RSA private key string. Correspondingly, the `verifying_secret_key` setting must contain an RSA public key string\n\n- ### `signing_secret_key`\nThe signing key utilized for signing the content of generated tokens has distinct requirements based on the signing protocol. \nFor HMAC signing, it should be a randomly generated string containing at least as many bits as dictated by the signing protocol. \nConversely, an RSA signing should be a string encompassing an RSA private key with a length of 2048 bits or more.\nAs Simple JWT defaults to 256-bit HMAC signing, the `signing_secret_key` setting automatically takes on the value of your Django project's `SECRET_KEY`. \nWhile this default is practical, developers should modify this setting to a value separate from the Django project's secret key. \nThis adjustment facilitates easier token signing key changes if the key is ever compromised.\n\n- ### `verifying_secret_key`\nThe verification key is employed to authenticate the contents of generated tokens. \nIn case an HMAC algorithm is indicated by the `algorithm` setting, the `verifying_secret_key` configuration is disregarded, and the `signing_secret_key` setting value will be utilized. \nHowever, if an RSA algorithm is designated by the `algorithm` setting, the `verifying_secret_key` parameter must be populated with an RSA public key string\n\n- ### `audience`\nThe audience claim is incorporated into generated tokens and/or verified within decoded tokens. \nIf configured as `None`, this element is omitted from tokens and isn't subjected to validation.\n\n- ### `issuer`\nThe issuer claim is added to generated tokens and/or validated within decoded tokens. \nIf configured as `None`, this attribute is omitted from tokens and isn't subjected to validation.\n\n- ### `jwk_url`\nThe JWK_URL serves the purpose of dynamically retrieving the required public keys for token signature verification. \nFor instance, with Auth0, you could configure it as 'https://yourdomain.auth0.com/.well-known/jwks.json'. \nIf set to `None`, this field is omitted from the token backend and remains inactive during validation.\n\n- ### `leeway`\nLeeway provides a buffer for the expiration time, which can be defined as an integer representing seconds or a datetime.timedelta object. \nFor further details, please consult the following link: https://pyjwt.readthedocs.io/en/latest/usage.html#expiration-time-claim-exp\n\n- ### `jti`\nThe claim is designated for storing a token's unique identifier, which is utilized to distinguish revoked tokens within the blacklist application. \nThere might be instances where an alternative claim other than the default \"jti\" claim needs to be employed for storing this value\n\n- ### `json_encoder`\nJSON Encoder class that will be used by the `PYJWT` to encode the `jwt_payload`.  \n\n\n\n## API Spec\n\nThe `JwtService` uses [PYJWT](https://pypi.org/project/PyJWT/) underneath.\n\n### _jwt_service.sign(payload: dict, headers: Dict[str, t.Any] = None, **jwt_config: t.Any) -\u003e str_\nCreates a jwt token for the provided payload. Also, you can override the default jwt config by using passing some keyword argument as a `jwt_config`\n\n### _jwt_service.sign_async(payload: dict, headers: Dict[str, t.Any] = None, **jwt_config: t.Any) -\u003e str_\nAsync action for `jwt_service.sign`\n\n### _jwt_service.decode(token: str, verify: bool = True, **jwt_config: t.Any) -\u003e t.Dict[str, t.Any]:_\nVerifies and decodes provided token. And raises a JWTException exception if the token is invalid or expired\n\n### _jwt_service.decode_async(token: str, verify: bool = True, **jwt_config: t.Any) -\u003e t.Dict[str, t.Any]:_\nAsync action for `jwt_service.decode`\n\n\n## License\n\nEllar is [MIT licensed](LICENSE).\n","project_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fpython-ellar%2Fellar-jwt","html_url":"https://awesome.ecosyste.ms/projects/github.com%2Fpython-ellar%2Fellar-jwt","lists_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fpython-ellar%2Fellar-jwt/lists"}