Skip to content
GitHub

Authentication

lexigram-auth provides authentication and authorization — JWT, OAuth2, password hashing, and role-based access control (RBAC). In a web application, most checks happen in the request pipeline using guards.


graph TD
    Req[Client Request] --> MW[Middleware: CORS / CSRF / Auth]
    MW --> Route[Router: match path]
    Route --> Guard[Guards: authenticate & authorize]
    Guard --> Handler[Controller handler]
ComponentScopeRunsUsed for
MiddlewareGlobalOutermostCORS, CSRF, rate limiting, auth context
GuardPer route/controllerAfter routingAuthentication, role checks

Apply guards to a controller or a single handler with @use_guards. The built-in AuthGuard requires a valid session or token; RoleGuard restricts by role.

from lexigram.web import Controller, get
from lexigram.web.security import use_guards, AuthGuard, RoleGuard
class ProfileController(Controller):
prefix = "/api/profile"
@get("/")
@use_guards(AuthGuard)
async def me(self) -> dict:
return {"status": "authenticated"}
@use_guards(RoleGuard("admin")) # applies to every route in the controller
class AdminController(Controller):
prefix = "/admin"

lexigram.web also re-exports concise shortcuts:

from lexigram.web import roles, guard
@roles("admin", "editor") # require any of these roles
@guard(MyCustomGuard) # apply a custom guard

AuthGuard and RoleGuard are abstract base classes — implement your own by subclassing and returning either success or a GuardRejection. Request data is available through the typed Request (e.g. request.ip, request.user):

from lexigram.web.security import AuthGuard
from lexigram.web import Request
class IPAllowlistGuard(AuthGuard):
allowed = {"127.0.0.1", "10.0.0.1"}
async def can_activate(self, request: Request) -> bool:
return request.ip in self.allowed

See the lexigram-auth package docs for the exact guard interface and built-in guards.


When a guard rejects a request, Lexigram returns a standardized HTTP error (as RFC 7807 Problem Details):

FailureHTTP status
Not authenticated401
Authenticated but not authorized403

Because the framework uses the Result pattern, services can also return auth errors directly and the web layer maps them to the right status code.


Add the auth provider and configure the auth section — JWT signing, password policy, and RBAC:

from lexigram.auth import AuthBundleProvider
app.add_provider(AuthBundleProvider())
application.yaml
auth:
enabled: true
token:
secret_key: "${LEX_AUTH__TOKEN__SECRET_KEY}"
algorithm: HS256
access_token_expire_minutes: 30
password:
min_length: 12
require_uppercase: true
require_digits: true
rbac:
enabled: true
default_role: viewer