Auth Guard
The AuthGuard factory from @stratal/framework/guards creates guards that check authentication and, optionally, permission. It works with AuthContext for authentication and with AccessService for permission checks — both supplied automatically when their respective modules are configured.
Authentication only
Section titled “Authentication only”Apply AuthGuard() without options to require authentication on a controller or route:
import { Controller, IController, Route, RouterContext } from 'stratal/router'import { UseGuards } from 'stratal/router'import { AuthGuard } from '@stratal/framework/guards'
@Controller('/api/profile')@UseGuards(AuthGuard())export class ProfileController implements IController { @Route({ response: profileSchema }) index(ctx: RouterContext) { // only authenticated users reach this handler return ctx.json({ profile: '...' }) }}When no permissions are provided, AuthGuard checks AuthContext.isAuthenticated(). If the user is not authenticated, it throws a UserNotAuthenticatedError (HTTP 401).
With permission checks
Section titled “With permission checks”Pass a permissions option to enforce access-control checks alongside authentication. Each entry is a 'resource:action' string:
@Controller('/api/admin/users')@UseGuards(AuthGuard({ permissions: 'users:ban' }))export class AdminUsersController implements IController { @Route({ response: usersSchema }) index(ctx: RouterContext) { // only authenticated users with 'users:ban' permission reach this handler return ctx.json({ users: [] }) }}permissions accepts a single string or an array. When you pass an array, every listed permission must be granted:
@UseGuards(AuthGuard({ permissions: ['posts:delete', 'admin:access'] }))A bare resource without an action (e.g. 'admin') is treated as a wildcard — the user passes if they have any action defined for that resource.
AuthGuard first verifies authentication (401 if not authenticated), then checks permissions through AccessService (403 if unauthorized). The permission check reads roles from AuthContext, so it doesn’t trigger an extra database query.
Per-route guards
Section titled “Per-route guards”Apply AuthGuard at the route level instead of the controller level when only some routes need authorization:
@Controller('/api/students')export class StudentsController implements IController { @Route({ response: studentsSchema }) @UseGuards(AuthGuard({ permissions: 'students:read' })) index(ctx: RouterContext) { // requires students:read permission }
@Route({ body: createStudentSchema, response: studentSchema }) @UseGuards(AuthGuard({ permissions: 'students:write' })) create(ctx: RouterContext) { // requires students:write permission }}Error types
Section titled “Error types”| Error | HTTP Status | When |
|---|---|---|
UserNotAuthenticatedError | 401 | User is not authenticated |
InsufficientPermissionsError | 403 | User is authenticated but lacks the required permissions |
Both errors are handled by Stratal’s global error handler and produce JSON error responses with localised messages.
Prerequisites
Section titled “Prerequisites”- AuthModule must be configured for any use of
AuthGuard. - For permission checks, pass an
accessControloption toAuthModule.forRootAsync()so thatAccessServiceis registered. See Access Control.
Next steps
Section titled “Next steps”- Auth for configuring authentication.
- Access Control for declaring resources and roles.
- Guards for the core guard system and writing custom guards.