Summary
The admin console needs to view and search audit trail history. The audit trail write pipeline (entity, BullMQ queue, processor, interceptor, decorators) was shipped in the MVP, but query endpoints were explicitly deferred as out-of-scope. This issue adds read-only endpoints so superadmins can browse, filter, and inspect audit log entries.
Endpoints
GET /audit-logs — Paginated list with filters
Query parameters (all optional):
| Param |
Type |
Description |
action |
string |
Exact match on audit action code (e.g. auth.login.success) |
actorId |
UUID |
Exact match on actor UUID |
actorUsername |
string |
Partial match (ILIKE) |
resourceType |
string |
Exact match (e.g. User, AnalysisPipeline) |
resourceId |
string |
Exact match on resource UUID |
from |
ISO 8601 |
Lower bound (inclusive) on occurredAt |
to |
ISO 8601 |
Upper bound (inclusive) on occurredAt |
search |
string |
Text search across actorUsername, action, resourceType |
page |
number |
Page number (default: 1) |
limit |
number |
Items per page (default: 10, max: 100) |
Response: { data: AuditLogItemResponseDto[], meta: PaginationMeta }
GET /audit-logs/:id — Single audit log detail
Returns the full audit log record including metadata JSONB field.
Access Control
Both endpoints restricted to SUPER_ADMIN via @UseJwtGuard(UserRole.SUPER_ADMIN).
Technical Notes
- New
AuditQueryService (separate from write-focused AuditService) handles query logic
- New
AuditController registered in existing AuditModule
- All queries use
filters: { softDelete: false } to bypass global MikroORM filter (AuditLog does not extend CustomBaseEntity)
- Default sort:
occurredAt DESC, id DESC
- LIKE special characters are escaped in search/partial-match filters
- Follows established patterns from
AdminService.ListUsers() and MoodleSyncController.GetSyncHistory()
Summary
The admin console needs to view and search audit trail history. The audit trail write pipeline (entity, BullMQ queue, processor, interceptor, decorators) was shipped in the MVP, but query endpoints were explicitly deferred as out-of-scope. This issue adds read-only endpoints so superadmins can browse, filter, and inspect audit log entries.
Endpoints
GET /audit-logs— Paginated list with filtersQuery parameters (all optional):
actionstringauth.login.success)actorIdUUIDactorUsernamestringresourceTypestringUser,AnalysisPipeline)resourceIdstringfromISO 8601occurredAttoISO 8601occurredAtsearchstringactorUsername,action,resourceTypepagenumberlimitnumberResponse:
{ data: AuditLogItemResponseDto[], meta: PaginationMeta }GET /audit-logs/:id— Single audit log detailReturns the full audit log record including metadata JSONB field.
Access Control
Both endpoints restricted to
SUPER_ADMINvia@UseJwtGuard(UserRole.SUPER_ADMIN).Technical Notes
AuditQueryService(separate from write-focusedAuditService) handles query logicAuditControllerregistered in existingAuditModulefilters: { softDelete: false }to bypass global MikroORM filter (AuditLog does not extend CustomBaseEntity)occurredAt DESC, id DESCAdminService.ListUsers()andMoodleSyncController.GetSyncHistory()