Services — CMS Frontend
Service Architecture Overview
The frontend uses TanStack Query as the server-state service layer. All API interactions are encapsulated in typed query/mutation hooks. The ApiClient handles transport concerns (headers, 401 retry). AuthContext manages session state. There is no additional service abstraction layer needed.
Backend Services (Unit 0 changes)
CORS Service (new)
- Service:
ServiceCollectionExtensions.AddCorsFrontendPolicy()
- Purpose: Register named CORS policy
"FrontendPolicy" for frontend SPA
- Configuration source:
IConfiguration → Cors:AllowedOrigins array
- Key settings:
WithOrigins(allowedOrigins) — from config
AllowAnyHeader() + AllowAnyMethod()
AllowCredentials() — required for httpOnly cookie
- dotnet-appsettings pattern:
AllowedOrigins stored in appsettings.json (production) and appsettings.Development.json (dev, e.g. ["http://localhost:5173"]); appsettings.local.json for developer-specific overrides
Frontend Services (TanStack Query hooks)
Auth Service (frontend/src/auth/)
AuthContext functions as the auth service — it is the single source of truth for authentication state.
| Operation |
Implementation |
Notes |
| Login |
POST /api/v1/auth/login → stores accessToken in memory |
httpOnly cookie set by server |
| Session restore |
POST /api/v1/auth/refresh on app mount → stores new accessToken |
Reads cookie automatically |
| Logout |
POST /api/v1/auth/revoke → clears in-memory token |
Server clears cookie |
| Token refresh (interceptor) |
POST /api/v1/auth/refresh on 401 → retry original request |
Centralised in ApiClient |
Availability Service (frontend/src/api/useAvailability.ts)
| Hook |
Query key |
Endpoint |
Stale time |
useAvailabilityStatus() |
['availability', 'status'] |
GET /api/v1/availability/status |
30s |
Users Service (frontend/src/api/useUsers.ts)
| Hook |
Query key |
Endpoint |
Notes |
useUsers() |
['users'] |
GET /api/v1/users |
Owner/Admin only |
useInviteUser() |
mutation |
POST /api/v1/users/invite |
Invalidates ['users'] on success |
Invitation Service (frontend/src/api/useInvitation.ts)
| Hook |
Query key |
Endpoint |
Notes |
useValidateInvitation(token) |
['invitation', token] |
GET /api/v1/users/validate-invitation?token= |
Public, no auth |
useCompleteSetup() |
mutation |
POST /api/v1/users/complete-setup |
Public, no auth |
Setup Service (frontend/src/api/useSetup.ts)
| Hook |
Query key |
Endpoint |
Notes |
useSetupStatus() |
['setup', 'status'] |
GET /api/v1/setup/status |
Used by InitGuard |
useCreateOwner() |
mutation |
POST /api/v1/setup/owner |
Used on /setup page |
Service Interaction Diagram