Skip to content

Migrating to 0.12

0.12 makes FastAPI integration explicit and adds trusted server-side provisioning and bound authentication dependencies.

Replace auth.mount(app)

FastAuth.mount() has been removed. Include the prefix-free router at the application's chosen prefix, then install FastAuth's application-wide security integration separately:

app.include_router(auth.router, prefix="/api/auth", tags=["auth"])
auth.add_middleware(app)

auth.add_middleware(app) registers the FastAuthError exception handler and installs CSRF and security-header middleware. It never includes routes or chooses their prefix.

If the host application supplies equivalent exception handling and security middleware, it can include auth.router without calling auth.add_middleware(app).

auth.as_asgi() remains a batteries-included standalone adapter. It includes the router at options.app.base_path and installs the FastAuth middleware.

Provision users from trusted server code

Use auth.api.create_user() in seeds, workers, webhook handlers, and other trusted application code:

user = await auth.api.create_user(
    email="admin@app.com",
    password="secure-password",
    metadata={"role": "admin"},
)

This creates a credential user without creating a session, issuing refresh tokens, or sending verification email.

Use bound dependency aliases

Required authentication dependencies are available directly on the initialized instance:

@app.get("/me")
async def me(user: auth.CurrentUser):
    return user


@app.get("/my-session")
async def my_session(session: auth.CurrentSession):
    return session

With postponed annotations, keep auth as a module-level binding. Explicit Depends(auth.depends.user()) and Depends(auth.depends.session()) remain available for factory- or closure-scoped instances.

Register events and hooks with decorators

auth.on_event() has been removed, and application hooks no longer need to reach through auth.context:

# Before
auth.on_event(UserCreated, record_event)
auth.context.hooks.register(HookPhase.BEFORE_CREATE, "user", transform_user)

# After
auth.on(UserCreated)(record_event)
auth.hook(HookPhase.BEFORE_CREATE, target="user")(transform_user)

Decorator syntax is the canonical form:

@auth.on(UserCreated)
async def record_event(event: UserCreated) -> None:
    ...


@auth.hook(HookPhase.BEFORE_CREATE, target="user")
async def transform_user(context: HookContext) -> User:
    ...

The decorators return the original functions. Event exception isolation and hook payload/error behavior are unchanged.