Authentication and JWT in FastAPI

Difficulty: Intermediate

Question

How do you implement JWT-based authentication in FastAPI?

Answer

FastAPI provides security utilities in `fastapi.security` for common auth schemes. For JWT:

1. Use `OAuth2PasswordBearer` to extract the Bearer token from the `Authorization` header 2. On login, verify credentials and issue a JWT using `python-jose` or `PyJWT` 3. Create a `get_current_user` dependency that decodes and validates the JWT 4. Inject `get_current_user` as a dependency in protected routes

FastAPI's `OAuth2PasswordBearer` also integrates with the Swagger UI, letting you authenticate directly from the docs.

Code examples

JWT auth flow

from fastapi import FastAPI, Depends, HTTPException, status
from fastapi.security import OAuth2PasswordBearer, OAuth2PasswordRequestForm
from jose import JWTError, jwt
from datetime import datetime, timedelta

app = FastAPI()
SECRET_KEY = "your-secret-key"
ALGORITHM = "HS256"
oauth2_scheme = OAuth2PasswordBearer(tokenUrl="/token")

def create_token(data: dict):
    expire = datetime.utcnow() + timedelta(minutes=30)
    return jwt.encode({data, "exp": expire}, SECRET_KEY, algorithm=ALGORITHM)

async def get_current_user(token: str = Depends(oauth2_scheme)):
    try:
        payload = jwt.decode(token, SECRET_KEY, algorithms=[ALGORITHM])
        username = payload.get("sub")
        if username is None:
            raise HTTPException(status_code=401, detail="Invalid token")
        return username
    except JWTError:
        raise HTTPException(status_code=401, detail="Invalid token")

@app.post("/token")
async def login(form: OAuth2PasswordRequestForm = Depends()):
    # verify form.username and form.password against DB...
    token = create_token({"sub": form.username})
    return {"access_token": token, "token_type": "bearer"}

@app.get("/me")
async def read_me(user: str = Depends(get_current_user)):
    return {"user": user}

Key points

Concepts covered

OAuth2, JWT, Bearer token, security schemes