SLA & Escalation
The SLA system in @nx/helpdesk tracks two deadlines per ticket: first response time and resolution time. When thresholds are crossed, BullMQ workers automatically escalate and dispatch notifications.
Default SLA Levels
| Priority | Code | Response | Resolution |
|---|---|---|---|
| Low | 100 | 24 hours | 72 hours |
| Normal | 200 | 8 hours | 24 hours |
| High | 300 | 4 hours | 12 hours |
| Urgent | 400 | 1 hour | 4 hours |
Data Model
SlaPolicy
| Column | Type | Description |
|---|---|---|
id | bigint | Snowflake ID |
name | jsonb | Policy name (i18n: {en, vi}) |
priority | smallint | Priority level (100/200/300/400) |
responseTimeMinutes | int | Allowed response time (minutes) |
resolutionTimeMinutes | int | Allowed resolution time (minutes) |
warningThresholdPercent | smallint | Warning threshold (default 75%) |
criticalThresholdPercent | smallint | Critical threshold (default 90%) |
escalationRules | jsonb[] | Auto-escalation rule definitions |
businessHoursOnly | boolean | Count only within business hours |
isActive | boolean | Whether the policy is in effect |
SlaTracker
Tracks SLA progress per ticket:
| Column | Type | Description |
|---|---|---|
ticketId | bigint | FK → Ticket |
slaPolicyId | bigint | FK → SlaPolicy |
responseDeadline | timestamp | Response deadline from ticket creation |
resolutionDeadline | timestamp | Resolution deadline |
firstResponseAt | timestamp | Actual first response timestamp |
resolvedAt | timestamp | Actual resolution timestamp |
firstResponseStatus / resolutionStatus | enum | OK / WARNING / BREACHED (SlaStatuses) |
warningTriggeredAt | timestamp | When the warning was sent |
breachTriggeredAt | timestamp | When the breach was recorded |
SlaEscalation
History of escalation events:
| Column | Type | Description |
|---|---|---|
ticketId | bigint | FK → Ticket |
level | smallint | Escalation level (1/2/3) |
reason | text | Reason for escalation |
escalatedAt | timestamp | Escalation timestamp |
handledBy | bigint | Agent who handled the escalation |
SLA Breach Flow (End-to-End)
Auto-Applied SLA Tags
| Tag | Condition | Description |
|---|---|---|
SLA_BREACHED | Exceeds 100% of deadline | SLA violated |
OVERDUE | Deadline has passed | Past resolution deadline |
CRITICAL_BREACH | Exceeds 150% of deadline | Critical violation, triggers re-assignment |
REST API
SLA policies are served under /sla-policies (RestPaths.SLA) by SlaController — full endpoint reference rendered live from /v1/api/helpdesk/doc/openapi.json. Endpoint tables are intentionally not hand-maintained.
SLA Use Cases
| Use Case | Description |
|---|---|
CreateSlaPolicyUseCase | Create a new SLA policy |
UpdateSlaPolicyUseCase | Update SLA parameters |
DeleteSlaPolicyUseCase | Remove a policy |
GetSlaPolicyByIdUseCase | Get policy details |
ListSlaPoliciesUseCase | List all policies |
InitializeSlaTrackerUseCase | Create tracker when ticket is created |
MarkFirstResponseUseCase | Record the first agent response |
MarkResolvedUseCase | Record ticket resolution |
CalculateBatchSlaStatusUseCase | Batch-calculate SLA statuses |
BulkMarkSlaWarningUseCase | Bulk-apply warning flags |
BulkMarkSlaBreachedUseCase | Bulk-apply breach flags |
TriggerSlaCheckUseCase | Manually trigger a check |
ProcessEscalationUseCase | Process a single escalation event |
RunSlaMonitorUseCase | Execute one SLA monitor scan pass |
Workers
| Worker | Queue | Frequency | Function |
|---|---|---|---|
sla-monitor.worker | helpdesk.sla-monitor | Cron (1 min) | Scans trackers approaching or past deadline |
escalation.worker | helpdesk.escalation | Delayed job | Handles Level 2 and Level 3 escalation |
Reassignment to a senior agent on Level 2+ is currently disabled in code (notification only). See Operations → Known Issues.
Compensation (CompensationCalculatorService)
When an SLA breach occurs, compensation is calculated against a matrix:
| Criterion | Description |
|---|---|
| Customer tier | VIP / PREMIUM / STANDARD |
| Ticket priority | LOW / NORMAL / HIGH / URGENT |
| Breach duration | Time elapsed past the deadline |
| Escalation level | Only triggers from Level 2 onward |
Results are persisted to the Compensation table for offline processing.