Skip to main content

Security Guards

Guards intercept every incoming request before it reaches a route handler. If a guard returns False, Nidus raises EUnauthorizedException (HTTP 401) and stops processing immediately.

Registering a guard

GetNidus
.UseGuard(
function: Boolean
begin
// Return True to allow, False to deny
Result := ValidateJWT(GetNidus.Request.Authorization);
end)
.Start(TAppModule.Create);

UseGuard accepts a TGuardCallback — a reference function that returns Boolean. The callback is stored in TNidus.FGuardCallback and evaluated on each call to LoadRouteModule.

How it fits in the request pipeline

LoadRouteModule(path, request)

├── [guard set?] → FGuardCallback()
│ └── False → raise EUnauthorizedException (HTTP 401)

├── [pipe set?] → Pipe.Validate(routeHandler, request)
│ └── messages? → return TReturnPair.Failure(EBadRequestException)

└── RouteParse.SelectRoute(path, request) → success

Source: TNidus.LoadRouteModule in Nidus.pas.

Accessing request data inside a guard

Inside the guard callback, use GetNidus.Request to inspect the current IRouteRequest:

.UseGuard(
function: Boolean
var LReq: IRouteRequest;
begin
LReq := GetNidus.Request;
Result := (LReq <> nil) and CheckToken(LReq.Authorization);
end)

IRouteRequest (defined in Nidus.Request) exposes the following methods:

MethodReturn typeDescription
HeaderTRequestDataRequest headers
ParamsTRequestDataRoute parameters
QuerysTRequestDataQuery-string parameters
BodystringRaw request body
HoststringHost name
ContentTypestringContent-Type header value
MethodstringHTTP method (GET, POST, …)
URLstringFull request URL
PortintegerServer port
AuthorizationstringAuthorization header value
AsObjectTObjectDeserialized body object (set by TParseJsonPipe)

Exception types

ExceptionHTTP statusRaised by
EUnauthorizedException401Guard returns False
EBadRequestException400Validation pipe failure
ENidusException (base)status from .StatusAny Nidus exception

Source: Nidus.Exception.