Flask API#

Flask integration for py oidc auth.

Flask view functions are synchronous. The base implementation is async, so this adapter uses asyncio.run to call the async methods.

Install:

pip install py-oidc-auth[flask]
conda install -c conda-forge py-oidc-auth-flask

Usage

from flask import Flask
from py_oidc_auth.flask_auth import FlaskOIDCAuth

auth = FlaskOIDCAuth(
    client_id="my client",
    client_secret="secret",
    discovery_url="https://idp.example.org/realms/demo/.well-known/openid-configuration",
    scopes="myscope profile email",
)

app = Flask(__name__)
app.register_blueprint(auth.create_auth_blueprint(prefix="/api"))

@app.get("/protected")
@auth.required()
def protected(token):
    return {"sub": token.sub}
class py_oidc_auth.flask_auth.FlaskOIDCAuth(client_id: str = '', discovery_url: str = '', client_secret: str | None = None, scopes: str = 'profile email', audience: str | None = None, proxy: str = '', claims: Dict[str, Any] | None = None, offline_access: bool = True, timeout_sec: int = 10)#

Reusable OpenID Connect helper for Flask.

This adapter provides:

The auth endpoints are suitable for browser based login and for programmatic token refresh.

required(claims: Dict[str, Any] | None = None, scopes: str = '') Callable[[F], F]#

Enforce authentication.

The decorated view receives the validated IDToken as its first positional argument.

Parameters:
  • claims – Optional claim constraints.

  • scopes – Space separated scope names the token must contain.

Returns:

Decorator for Flask views.

Example

@app.get("/admin")
@auth.required(claims={"groups": ["admins"]}, scopes="admin")
def admin(token):
    return {"sub": token.sub}
optional(claims: Dict[str, Any] | None = None, scopes: str = '') Callable[[F], F]#

Allow anonymous access.

The decorated view receives IDToken or None as its first positional argument.

Parameters:
  • claims – Optional claim constraints.

  • scopes – Space separated scope names.

Returns:

Decorator for Flask views.

Example

@app.get("/feed")
@auth.optional()
def feed(token):
    if token:
        return {"message": f"Welcome {token.preferred_username}"}
    return {"message": "Welcome guest"}
create_auth_blueprint(prefix: str = '', login: str = '/auth/v2/login', callback: str = '/auth/v2/callback', token: str = '/auth/v2/token', device_flow: str | None = '/auth/v2/device', logout: str | None = '/auth/v2/logout', userinfo: str | None = '/auth/v2/userinfo') flask.Blueprint#

Build a Flask flask.Blueprint with standard auth routes.

Each route can be disabled by passing None for its path.

Parameters:
  • prefix – URL prefix for all routes.

  • login – Path for login.

  • callback – Path for callback.

  • token – Path for token exchange and refresh.

  • device_flow – Path for starting the device flow.

  • logout – Path for logout.

  • userinfo – Path for userinfo.

Returns:

A blueprint ready to be registered on your app.

Request examples

GET /auth/v2/login?redirect_uri=https%3A%2F%2Fapp.example.org%2Fcallback HTTP/1.1
Host: app.example.org
POST /auth/v2/token HTTP/1.1
Host: app.example.org
Content-Type: application/x-www-form-urlencoded

refresh_token=ref