Python Server SDK
Verify ezAuth JWTs in your own FastAPI or Starlette backend. Fetches and caches JWKS keys automatically.
Installation
pip install ezauth-sdk
Quick Start
Add the middleware to your FastAPI app to protect all routes:
from fastapi import FastAPI
from ezauth_sdk import EZAuthMiddleware
app = FastAPI()
app.add_middleware(
EZAuthMiddleware,
auth_domain="https://auth.example.com",
public_paths=["/health", "/docs", "/openapi.json"],
)
@app.get("/protected")
async def protected(request):
auth = request.state.auth
return {
"user_id": auth.user_id,
"session_id": auth.session_id,
}
How It Works
- The middleware extracts the JWT from the
__sessioncookie orAuthorization: Bearerheader - It decodes the JWT header to get the
kid(key ID) - It fetches the matching public key from your ezAuth instance's JWKS endpoint (
/.well-known/jwks.json) - It verifies the JWT signature using RS256
- On success, it sets
request.state.authwith the user's info - On failure, it returns
401 Unauthorized
EZAuthMiddleware
Parameters
| Parameter | Type | Default | Description |
|---|---|---|---|
auth_domain | str | — | Your EZAuth instance URL (e.g., https://auth.example.com) |
cookie_name | str | "__session" | Name of the session cookie to read |
audience | str | None | None | Expected JWT audience claim (optional) |
public_paths | list[str] | [] | Paths that skip authentication |
AuthState
After successful authentication, request.state.auth is an AuthState object:
| Attribute | Type | Description |
|---|---|---|
user_id | str | The authenticated user's ID (from JWT sub claim) |
session_id | str | The session ID (from JWT sid claim) |
claims | dict | All decoded JWT claims |
authenticate_request()
For more control, use the function directly instead of the middleware:
from ezauth_sdk import authenticate_request, AuthenticationError
from ezauth_sdk.jwks import JWKSClient
jwks_client = JWKSClient("https://auth.example.com")
@app.get("/custom-auth")
async def custom_auth(request):
try:
auth = await authenticate_request(request, jwks_client)
return {"user_id": auth.user_id}
except AuthenticationError as e:
return JSONResponse(status_code=401, content={"error": e.message})
Parameters
| Parameter | Type | Default | Description |
|---|---|---|---|
request | Request | — | Starlette/FastAPI request object |
jwks_client | JWKSClient | — | JWKS client instance |
cookie_name | str | "__session" | Cookie name |
audience | str | None | None | Expected audience |
JWKSClient
The JWKSClient fetches and caches JWKS keys from your ezAuth instance:
from ezauth_sdk.jwks import JWKSClient
client = JWKSClient("https://auth.example.com")
key = await client.get_signing_key("key-id")
Keys are cached in memory. The client refetches when an unknown kid is encountered.
AuthenticationError
from ezauth_sdk import AuthenticationError
try:
auth = await authenticate_request(request, jwks_client)
except AuthenticationError as e:
print(e.message) # e.g. "No authentication token found"
Exports
| Export | Description |
|---|---|
EZAuthMiddleware | Starlette/FastAPI middleware class |
authenticate_request | Standalone function for custom auth logic |
AuthState | Dataclass with user_id, session_id, claims |
AuthenticationError | Exception raised on auth failure |