Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

🛠 Native JWT support #3305

Open
wants to merge 28 commits into
base: master
Choose a base branch
from
Open

🛠 Native JWT support #3305

wants to merge 28 commits into from

Conversation

k4black
Copy link

@k4black k4black commented May 28, 2021

Relevance

About half of the modern internet uses raw JWT (the other half uses OAuth2, which is already supported).
I think that in such a modern library as fastapi, native support of JWT will be a big advantage.

Existed solutions

Only 1 external lib: github:fastapi-jwt-auth (192 stars) - an flask-jwt-auth customization.

The following drawbacks are significant:

  1. poorly supported (last updated in 2020)
  2. depends on the original library
  3. DOES NOT match the fastapi security style (Security/Depends function args wrapper)
  4. no openapi specification generation

Existed Issues and Pull Requests:

  • Searching 'jwt' or 'json web tokens' - 'No results matched' (except docs example)

Features

  • bearer/cookie token place
  • access/refresh tokens
  • time expiring tokens
  • auto_error=False support
  • openapi specification generation
  • fresh token demand
  • token revocation
  • cookies name selecting
  • docs examples (after approval)

Requrements

python-jose for tokens interaction and pytest-mock for testing time-dependent functions.

Usage example

All available use cases can be found in the test files. The simplest example is provided below:

app = FastAPI()

access_security = JwtAccessBearer(secret_key="secret_key")

@app.post("/auth")
def auth():
    subject = {"username": "username", "role": "user"}
    access_token = access_security.create_access_token(subject=subject)
    return {"access_token": access_token, "refresh_token": None}

@app.get("/users/me")
def read_current_user(credentials: JwtAuthorizationCredentials = Security(access_security)):
    return {"username": credentials["username"], "role": credentials["role"]}

Any suggestions for improvement are gladly discussed!

@acutaia
Copy link

acutaia commented Jun 7, 2021

@k4black in security docs @tiangolo in the past used Pyjwt but later he moved to python-jose PR [#1610] so I think we should consider using python-jose for your pull request 🤔

@k4black
Copy link
Author

k4black commented Jun 7, 2021

@acutaia
I saw this warning in docs, however, there were no arguments in favour of a younger library. Initially I used python-jose 😃, but migrate to PyJWT, as the most popular library according to jwt.io :libraries:python.
Although I agree that to comply with the general style, there may be a need to rewrite it with python-jose. I'll work on it

Cleaning a bit the code
@k4black
Copy link
Author

k4black commented Jun 16, 2021

@tiangolo Can you approve or decline this PR, please

@jakemanger
Copy link

Is this going to be approved or has this just been ignored? Seems like a nice, easy way to add authentication with the option of refresh tokens to me.


# Check token exist
if refresh_token is None:
if not self.auto_error:
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Do not reverse the condition add the raise keyword to the if block.

) -> Optional[JwtAuthorizationCredentials]:
payload = self._get_payload(bearer, cookie)

if payload:
Copy link
Contributor

@cikay cikay Feb 3, 2022

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This is where you should reverse the condition the success case should be at the bottom. It is called early return or fast fail.

@tiangolo tiangolo added the feature New feature or request label Jun 28, 2023
@JanBeelte
Copy link

Is there any chance that this PR or comparable functionality will be merged soon?
What are the next steps here @tiangolo @cikay @k4black @acutaia , I might be willing to take over some work.
Would be very handy to have jwt support out of the box!

@and-sm
Copy link

and-sm commented Jun 20, 2024

@tiangolo, any update?

@jpmckinney
Copy link

python-jose is unmaintained. Please do not use it.

@nsteinmetz
Copy link

python-jose is unmaintained. Please do not use it.

latest version of fastapi-jwt allows to use authlib instead of python-jose (still present as fallback)

@Pandede
Copy link

Pandede commented Nov 21, 2024

Any update?

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
feature New feature or request
Projects
None yet
Development

Successfully merging this pull request may close these issues.

10 participants