Before hooks
Before hooks run before an endpoint executes. Use them to validate requests, modify context, or return early with an error.Enforce an email domain restriction
auth.ts
Modify request context
Return a{ context } object to replace the context before the endpoint runs:
auth.ts
After hooks
After hooks run after an endpoint executes. Use them to react to changes or modify the response.Notify a channel when a new user registers
auth.ts
The ctx object
createAuthMiddleware receives a ctx object with the following properties:
| Property | Description |
|---|---|
ctx.path | Current endpoint path |
ctx.body | Parsed request body (POST requests) |
ctx.headers | Request headers |
ctx.request | The raw request object (may not exist in server-only endpoints) |
ctx.query | URL query parameters |
ctx.context | Auth-specific context (session, cookies, adapter, etc.) |
Sending responses
JSON
Redirects
Cookies
Throwing errors
The ctx.context object
The context property inside ctx provides auth-specific data.
newSession
The session created by the endpoint. Only available in after hooks.
returned
The value returned by the endpoint (a successful response or an APIError). Only available in after hooks.
responseHeaders
Response headers added by endpoints and hooks that ran before this one.
authCookies
Better Auth’s predefined cookie configuration:
secret
The auth instance secret: ctx.context.secret.
password
Password utilities:
ctx.context.password.hash(password)— hash a password.ctx.context.password.verify({ password, hash })— verify a password against a hash.
adapter
Exposes findOne, findMany, create, delete, update, and updateMany. Prefer using your ORM directly for most queries.
internalAdapter
Higher-level internal calls like createUser, createSession, and updateSession. Useful when you want databaseHooks and secondary storage support to apply automatically.
generateId
Generate a new ID: ctx.context.generateId().
runInBackground
Schedule a fire-and-forget task to run after the response is sent. Use for analytics, cleanup, and rate-limit updates:
auth.ts
runInBackgroundOrAwait
Defers the task when a background task handler is configured; awaits it otherwise. Use for operations that must eventually complete, like sending welcome emails:
auth.ts
Reusable hooks
If you need to share hook logic across multiple projects or endpoints, package it as a plugin. Plugins support the samehooks API with an additional matcher function for selective application.