Loading…
Loading…
Explains how the Admin API Authorization Filter secures endpoints by validating request paths, checking roles, and enforcing platform operator and data
The AdminAuthorizationFilter is a security component that intercepts all incoming HTTP requests to the Admin API. It functions as a servlet filter, executing before the request reaches its intended controller endpoint.
Its primary purpose is to provide a robust, layered defense for the Admin API. It enforces several critical security checks:
ADMIN) to access a given endpoint.The filter acts as a gatekeeper. If a request passes all checks, the filter enriches the request with authorization attributes and passes it down the filter chain. If any check fails, the filter immediately halts processing and returns an appropriate HTTP error response (e.g., 400 Bad Request or 403 Forbidden).
The AdminAuthorizationFilter processes each request through a sequence of security checks within its doFilterInternal method. The logic is designed to fail-fast, rejecting invalid requests as early as possible.
flowchart TD
subgraph "AdminAuthorizationFilter"
A[Request In] --> B{Path Safe?};
B -- No --> C[HTTP 400 Bad Request<br/>S2R-ADM-0400];
B -- Yes --> D{Auth Required?};
D -- No --> E[Continue to Controller];
D -- Yes --> F{Open Mode Active?};
F -- Yes --> G[Synthesize Admin Principal<br/>Continue to Controller];
F -- No --> H[Build Auth Context];
H --> I{Path is /admin/v1/me?};
I -- Yes --> E;
I -- No --> J{Actor Role >= Required Role?};
J -- No --> K[HTTP 403 Forbidden<br/>S2R-ADM-0403];
J -- Yes --> L{Platform Operator Required?};
L -- No --> M{Restricted Platform Operator?};
L -- Yes --> N{Actor is Platform Operator?};
N -- No --> O[HTTP 403 Forbidden<br/>S2R-ADM-0407];
N -- Yes --> M;
M -- No --> E;
M -- Yes --> P{Path Allowed for Operator?};
P -- Yes --> E;
P -- No --> Q[HTTP 403 Forbidden<br/>S2R-ADM-0408];
end
C --> R[Response Out]
K --> R
O --> R
Q --> R
E --> S[Backend Service]The sequence of operations is as follows:
Path Validation: The filter first inspects the raw request URI using the hasUnsafePath method. It rejects any request containing path traversal sequences (..), backslashes (\), path parameters (;), empty path segments (//), or certain percent-encoded characters (%2e, %2f, %5c). This prevents authorization bypasses that could result from differences in how paths are parsed by security layers versus the routing layer. If the path is deemed unsafe, the filter returns an HTTP 400 Bad Request with error code S2R-ADM-0400.
NOTE
This path validation is a "defence in depth" measure. The primary authorization logic now uses the same parsed, normalized request path that the Spring routing mechanism uses, making it resilient to these bypass techniques. However, this initial check remains to reject malformed requests early.
Role Exemption Check: The filter consults the AdminAuthorizationService to determine the required AppRole for the request path. If the path requires AppRole.NONE, it is considered public. The filter immediately passes the request to the next filter in the chain without further checks.
Open Mode Check: If the platform has no identity providers configured, it operates in "open mode". The filter detects this via authorizationService.isOpenMode(). In this mode, all RBAC checks are bypassed. The filter synthesizes a temporary, super-administrator principal for the request with the ADMIN role, full platform operator privileges, and full data access. This ensures that an unconfigured instance is not locked out of its own control plane. The response includes the header X-S2R-Auth-Mode: open.
Authentication Context Building: For all other requests, the filter calls authorizationService.buildContext() to parse headers and establish the actor's identity, including their email, role (AppRole), and boolean flags for platformOperator and dataAccess. These details are then attached to the HttpServletRequest as attributes for downstream components.
/me Endpoint Exemption: Requests to the exact path /admin/v1/me are a special case. If the request has a resolved actor email, it is allowed to proceed without further role checks, enabling any authenticated user to retrieve their own identity information.
Role-Based Access Control (RBAC): The filter compares the actor's role from the AuthContext with the requiredRole for the path. It uses an atLeast check, meaning roles have a hierarchy (e.g., ADMIN satisfies a requirement for USER). If the actor's role is insufficient, the filter returns an HTTP 403 Forbidden with error code S2R-ADM-0403.
Platform Operator Gate: Certain administrative actions, such as managing tenants or platform-wide configurations, require a "platform operator" privilege. If authorizationService.requiresPlatformOperator(request) returns true and the actor's context has platformOperator set to false, the request is denied with an HTTP 403 Forbidden and error code S2R-ADM-0407. This prevents tenant-level administrators from accessing cross-tenant resources.
Data Access Wall: To support a "restricted platform operator" role that can manage the platform without accessing tenant data, an inverse check is performed. If an actor has platformOperator=true but dataAccess=false, they are only allowed to access a minimal set of paths required for fleet management (determined by isPlatformOperatorAllowedPath). Access to any other path is denied with an HTTP 403 Forbidden and error code S2R-ADM-0408. Actors who are not platform operators or who have dataAccess=true are not subject to this restriction.
Success: If a request passes all applicable checks, the filter invokes filterChain.doFilter(request, response) to pass control to the next component in the chain, ultimately leading to the target controller.
When a request is successfully processed, the filter adds the following attributes to the HttpServletRequest object for use by downstream components. The source defines these via AdminAuthorizationService constants.
| Attribute Constant Name | Description |
|---|---|
ATTR_ACTOR_EMAIL | The email address of the authenticated actor. In "open mode," this defaults to open-mode@local. |
ATTR_ACTOR_ROLE | The roleKey string of the actor's assigned AppRole. |
ATTR_CORRELATION_ID | A unique ID for tracing the request through the system. |
ATTR_PLATFORM_OPERATOR | A boolean indicating if the actor has platform operator privileges. |
ATTR_DATA_ACCESS | A boolean indicating if the actor is permitted to access tenant-specific or customer data. |
The filter adds the following headers to the HttpServletResponse.
| Header | Description |
|---|---|
X-Correlation-Id | A unique ID for tracing the request, mirrored from the request attribute. |
X-S2R-Auth-Mode | Set to open only when the platform is operating in "open mode." The header is not present otherwise. |
The filter's behavior can be customized with the following system setting, which is retrieved from the SystemSettingRepository.
| Name | Type | Default | Description |
|---|---|---|---|
access_denied_contact_message | String | You do not have access to this application. Please contact your administrator. | A custom message to include in the S2R-ADM-0403 error response when a user is denied access due to insufficient role permissions. |
When the filter denies a request, it returns a JSON error payload and logs a warning. The error codes are specific to the reason for denial.
| Error Code | HTTP Status | Meaning | Example Response |
|---|---|---|---|
S2R-ADM-0400 | 400 Bad Request | The request URI was rejected because it contained unsafe patterns like path traversal (..), backslashes (\), path parameters (;), empty segments (//), or disallowed percent-encoded characters. | json<br/>{"error":{"code":"S2R-ADM-0400","message":"Malformed request path."}}<br/> |
S2R-ADM-0403 | 403 Forbidden | The authenticated actor's role is not sufficient to perform the requested action. | json<br/>{"error":{"code":"S2R-ADM-0403","message":"Forbidden","details":{"requiredRole":"ADMIN","contactMessage":"You do not have access to this application. Please contact your administrator."}}}<br/> |
S2R-ADM-0407 | 403 Forbidden | The action requires a platform operator, but the authenticated actor is a tenant-level administrator. | json<br/>{"error":{"code":"S2R-ADM-0407","message":"This action requires a platform-operator role; tenant administrators cannot manage other tenants or the tenant registry.","details":{"requiredRole":"ADMIN","requiresPlatformOperator":true}}}<br/> |
S2R-ADM-0408 | 403 Forbidden | A restricted platform operator (with dataAccess=false) attempted to access a path that is not on the explicit allow-list for fleet management, which could expose tenant data. | json<br/>{"error":{"code":"S2R-ADM-0408","message":"Platform operators manage the fleet only and may not access customer or tenant data.","details":{"requiredRole":"ADMIN","dataAccess":false}}}<br/> |
ADMIN) used throughout the system for RBAC.