services-as-software 0.1.0 → 2.0.1
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/.turbo/turbo-build.log +5 -0
- package/CHANGELOG.md +10 -0
- package/README.md +235 -225
- package/dist/client.d.ts +25 -0
- package/dist/client.d.ts.map +1 -0
- package/dist/client.js +103 -0
- package/dist/client.js.map +1 -0
- package/dist/endpoint.d.ts +102 -0
- package/dist/endpoint.d.ts.map +1 -0
- package/dist/endpoint.js +96 -0
- package/dist/endpoint.js.map +1 -0
- package/dist/entities/billing.d.ts +60 -0
- package/dist/entities/billing.d.ts.map +1 -0
- package/dist/entities/billing.js +954 -0
- package/dist/entities/billing.js.map +1 -0
- package/dist/entities/customers.d.ts +45 -0
- package/dist/entities/customers.d.ts.map +1 -0
- package/dist/entities/customers.js +679 -0
- package/dist/entities/customers.js.map +1 -0
- package/dist/entities/delivery.d.ts +59 -0
- package/dist/entities/delivery.d.ts.map +1 -0
- package/dist/entities/delivery.js +890 -0
- package/dist/entities/delivery.js.map +1 -0
- package/dist/entities/index.d.ts +114 -0
- package/dist/entities/index.d.ts.map +1 -0
- package/dist/entities/index.js +89 -0
- package/dist/entities/index.js.map +1 -0
- package/dist/entities/operations.d.ts +59 -0
- package/dist/entities/operations.d.ts.map +1 -0
- package/dist/entities/operations.js +1010 -0
- package/dist/entities/operations.js.map +1 -0
- package/dist/entities/orchestration.d.ts +52 -0
- package/dist/entities/orchestration.d.ts.map +1 -0
- package/dist/entities/orchestration.js +883 -0
- package/dist/entities/orchestration.js.map +1 -0
- package/dist/entities/services.d.ts +50 -0
- package/dist/entities/services.d.ts.map +1 -0
- package/dist/entities/services.js +805 -0
- package/dist/entities/services.js.map +1 -0
- package/dist/helpers.d.ts +362 -0
- package/dist/helpers.d.ts.map +1 -0
- package/dist/helpers.js +400 -0
- package/dist/helpers.js.map +1 -0
- package/dist/index.d.ts +17 -215
- package/dist/index.d.ts.map +1 -0
- package/dist/index.js +18 -172
- package/dist/index.js.map +1 -0
- package/dist/provider.d.ts +85 -0
- package/dist/provider.d.ts.map +1 -0
- package/dist/provider.js +158 -0
- package/dist/provider.js.map +1 -0
- package/dist/service.d.ts +43 -0
- package/dist/service.d.ts.map +1 -0
- package/dist/service.js +206 -0
- package/dist/service.js.map +1 -0
- package/dist/types.d.ts +469 -0
- package/dist/types.d.ts.map +1 -0
- package/dist/types.js +5 -0
- package/dist/types.js.map +1 -0
- package/examples/client-usage.ts +82 -0
- package/examples/translation-service.ts +227 -0
- package/package.json +24 -38
- package/src/client.ts +132 -0
- package/src/endpoint.ts +144 -0
- package/src/entities/billing.ts +1037 -0
- package/src/entities/customers.ts +740 -0
- package/src/entities/delivery.ts +974 -0
- package/src/entities/index.ts +157 -0
- package/src/entities/operations.ts +1099 -0
- package/src/entities/orchestration.ts +956 -0
- package/src/entities/services.ts +872 -0
- package/src/helpers.ts +474 -0
- package/src/index.ts +97 -0
- package/src/provider.ts +183 -0
- package/src/service.test.ts +195 -0
- package/src/service.ts +266 -0
- package/src/types.ts +543 -0
- package/tsconfig.json +9 -0
|
@@ -0,0 +1,1099 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Operations Entity Types (Nouns)
|
|
3
|
+
*
|
|
4
|
+
* Service operations: SLA, SLO, ServiceIncident, SupportTicket, ServiceFeedback, ServiceMetric
|
|
5
|
+
*
|
|
6
|
+
* @packageDocumentation
|
|
7
|
+
*/
|
|
8
|
+
|
|
9
|
+
import type { Noun } from 'ai-database'
|
|
10
|
+
|
|
11
|
+
// =============================================================================
|
|
12
|
+
// SLA
|
|
13
|
+
// =============================================================================
|
|
14
|
+
|
|
15
|
+
/**
|
|
16
|
+
* SLA entity
|
|
17
|
+
*
|
|
18
|
+
* Service Level Agreement.
|
|
19
|
+
*/
|
|
20
|
+
export const SLA: Noun = {
|
|
21
|
+
singular: 'sla',
|
|
22
|
+
plural: 'slas',
|
|
23
|
+
description: 'A Service Level Agreement defining commitments',
|
|
24
|
+
|
|
25
|
+
properties: {
|
|
26
|
+
// Identity
|
|
27
|
+
name: {
|
|
28
|
+
type: 'string',
|
|
29
|
+
description: 'SLA name',
|
|
30
|
+
},
|
|
31
|
+
description: {
|
|
32
|
+
type: 'string',
|
|
33
|
+
optional: true,
|
|
34
|
+
description: 'SLA description',
|
|
35
|
+
},
|
|
36
|
+
version: {
|
|
37
|
+
type: 'string',
|
|
38
|
+
optional: true,
|
|
39
|
+
description: 'SLA version',
|
|
40
|
+
},
|
|
41
|
+
|
|
42
|
+
// Tier
|
|
43
|
+
tier: {
|
|
44
|
+
type: 'string',
|
|
45
|
+
optional: true,
|
|
46
|
+
description: 'SLA tier',
|
|
47
|
+
examples: ['basic', 'standard', 'premium', 'enterprise'],
|
|
48
|
+
},
|
|
49
|
+
|
|
50
|
+
// Availability
|
|
51
|
+
uptimeTarget: {
|
|
52
|
+
type: 'number',
|
|
53
|
+
optional: true,
|
|
54
|
+
description: 'Uptime target percentage (e.g., 99.9)',
|
|
55
|
+
},
|
|
56
|
+
uptimeCalculation: {
|
|
57
|
+
type: 'string',
|
|
58
|
+
optional: true,
|
|
59
|
+
description: 'How uptime is calculated',
|
|
60
|
+
examples: ['monthly', 'quarterly', 'yearly'],
|
|
61
|
+
},
|
|
62
|
+
|
|
63
|
+
// Response Times
|
|
64
|
+
responseTimeTarget: {
|
|
65
|
+
type: 'number',
|
|
66
|
+
optional: true,
|
|
67
|
+
description: 'Target response time (ms)',
|
|
68
|
+
},
|
|
69
|
+
responseTimeP50: {
|
|
70
|
+
type: 'number',
|
|
71
|
+
optional: true,
|
|
72
|
+
description: 'P50 response time target (ms)',
|
|
73
|
+
},
|
|
74
|
+
responseTimeP99: {
|
|
75
|
+
type: 'number',
|
|
76
|
+
optional: true,
|
|
77
|
+
description: 'P99 response time target (ms)',
|
|
78
|
+
},
|
|
79
|
+
|
|
80
|
+
// Support
|
|
81
|
+
supportResponseTime: {
|
|
82
|
+
type: 'string',
|
|
83
|
+
optional: true,
|
|
84
|
+
description: 'Support response time target',
|
|
85
|
+
},
|
|
86
|
+
supportHours: {
|
|
87
|
+
type: 'string',
|
|
88
|
+
optional: true,
|
|
89
|
+
description: 'Support hours',
|
|
90
|
+
examples: ['24/7', 'business-hours', '9-5'],
|
|
91
|
+
},
|
|
92
|
+
supportChannels: {
|
|
93
|
+
type: 'string',
|
|
94
|
+
array: true,
|
|
95
|
+
optional: true,
|
|
96
|
+
description: 'Support channels',
|
|
97
|
+
examples: ['email', 'chat', 'phone', 'slack'],
|
|
98
|
+
},
|
|
99
|
+
|
|
100
|
+
// Credits
|
|
101
|
+
creditPolicy: {
|
|
102
|
+
type: 'json',
|
|
103
|
+
optional: true,
|
|
104
|
+
description: 'Credit policy for SLA breaches',
|
|
105
|
+
},
|
|
106
|
+
maxCredit: {
|
|
107
|
+
type: 'number',
|
|
108
|
+
optional: true,
|
|
109
|
+
description: 'Maximum credit percentage',
|
|
110
|
+
},
|
|
111
|
+
|
|
112
|
+
// Exclusions
|
|
113
|
+
exclusions: {
|
|
114
|
+
type: 'string',
|
|
115
|
+
array: true,
|
|
116
|
+
optional: true,
|
|
117
|
+
description: 'SLA exclusions',
|
|
118
|
+
},
|
|
119
|
+
maintenanceWindows: {
|
|
120
|
+
type: 'json',
|
|
121
|
+
optional: true,
|
|
122
|
+
description: 'Scheduled maintenance windows',
|
|
123
|
+
},
|
|
124
|
+
|
|
125
|
+
// Dates
|
|
126
|
+
effectiveFrom: {
|
|
127
|
+
type: 'date',
|
|
128
|
+
optional: true,
|
|
129
|
+
description: 'Effective from date',
|
|
130
|
+
},
|
|
131
|
+
effectiveUntil: {
|
|
132
|
+
type: 'date',
|
|
133
|
+
optional: true,
|
|
134
|
+
description: 'Effective until date',
|
|
135
|
+
},
|
|
136
|
+
|
|
137
|
+
// Status
|
|
138
|
+
status: {
|
|
139
|
+
type: 'string',
|
|
140
|
+
description: 'SLA status',
|
|
141
|
+
examples: ['draft', 'active', 'superseded', 'expired'],
|
|
142
|
+
},
|
|
143
|
+
},
|
|
144
|
+
|
|
145
|
+
relationships: {
|
|
146
|
+
service: {
|
|
147
|
+
type: 'ProductizedService',
|
|
148
|
+
description: 'Service this SLA covers',
|
|
149
|
+
},
|
|
150
|
+
objectives: {
|
|
151
|
+
type: 'SLO[]',
|
|
152
|
+
description: 'Service level objectives',
|
|
153
|
+
},
|
|
154
|
+
incidents: {
|
|
155
|
+
type: 'ServiceIncident[]',
|
|
156
|
+
description: 'Related incidents',
|
|
157
|
+
},
|
|
158
|
+
},
|
|
159
|
+
|
|
160
|
+
actions: [
|
|
161
|
+
'create',
|
|
162
|
+
'update',
|
|
163
|
+
'activate',
|
|
164
|
+
'supersede',
|
|
165
|
+
'expire',
|
|
166
|
+
],
|
|
167
|
+
|
|
168
|
+
events: [
|
|
169
|
+
'created',
|
|
170
|
+
'updated',
|
|
171
|
+
'activated',
|
|
172
|
+
'superseded',
|
|
173
|
+
'expired',
|
|
174
|
+
'breached',
|
|
175
|
+
],
|
|
176
|
+
}
|
|
177
|
+
|
|
178
|
+
// =============================================================================
|
|
179
|
+
// SLO
|
|
180
|
+
// =============================================================================
|
|
181
|
+
|
|
182
|
+
/**
|
|
183
|
+
* SLO entity
|
|
184
|
+
*
|
|
185
|
+
* Service Level Objective.
|
|
186
|
+
*/
|
|
187
|
+
export const SLO: Noun = {
|
|
188
|
+
singular: 'slo',
|
|
189
|
+
plural: 'slos',
|
|
190
|
+
description: 'A Service Level Objective defining a specific target',
|
|
191
|
+
|
|
192
|
+
properties: {
|
|
193
|
+
// Identity
|
|
194
|
+
name: {
|
|
195
|
+
type: 'string',
|
|
196
|
+
description: 'SLO name',
|
|
197
|
+
},
|
|
198
|
+
description: {
|
|
199
|
+
type: 'string',
|
|
200
|
+
optional: true,
|
|
201
|
+
description: 'SLO description',
|
|
202
|
+
},
|
|
203
|
+
|
|
204
|
+
// Metric
|
|
205
|
+
metric: {
|
|
206
|
+
type: 'string',
|
|
207
|
+
description: 'Metric being measured',
|
|
208
|
+
examples: ['availability', 'latency', 'throughput', 'error-rate', 'success-rate'],
|
|
209
|
+
},
|
|
210
|
+
metricQuery: {
|
|
211
|
+
type: 'string',
|
|
212
|
+
optional: true,
|
|
213
|
+
description: 'Query to calculate metric',
|
|
214
|
+
},
|
|
215
|
+
|
|
216
|
+
// Target
|
|
217
|
+
target: {
|
|
218
|
+
type: 'number',
|
|
219
|
+
description: 'Target value',
|
|
220
|
+
},
|
|
221
|
+
comparison: {
|
|
222
|
+
type: 'string',
|
|
223
|
+
description: 'Comparison operator',
|
|
224
|
+
examples: ['>=', '<=', '>', '<', '='],
|
|
225
|
+
},
|
|
226
|
+
unit: {
|
|
227
|
+
type: 'string',
|
|
228
|
+
optional: true,
|
|
229
|
+
description: 'Unit of measure',
|
|
230
|
+
},
|
|
231
|
+
|
|
232
|
+
// Window
|
|
233
|
+
windowType: {
|
|
234
|
+
type: 'string',
|
|
235
|
+
description: 'Window type',
|
|
236
|
+
examples: ['rolling', 'calendar'],
|
|
237
|
+
},
|
|
238
|
+
windowDuration: {
|
|
239
|
+
type: 'string',
|
|
240
|
+
optional: true,
|
|
241
|
+
description: 'Window duration',
|
|
242
|
+
examples: ['30d', '7d', '1h', '1m'],
|
|
243
|
+
},
|
|
244
|
+
|
|
245
|
+
// Error Budget
|
|
246
|
+
errorBudget: {
|
|
247
|
+
type: 'number',
|
|
248
|
+
optional: true,
|
|
249
|
+
description: 'Error budget (as percentage)',
|
|
250
|
+
},
|
|
251
|
+
errorBudgetRemaining: {
|
|
252
|
+
type: 'number',
|
|
253
|
+
optional: true,
|
|
254
|
+
description: 'Remaining error budget',
|
|
255
|
+
},
|
|
256
|
+
burnRate: {
|
|
257
|
+
type: 'number',
|
|
258
|
+
optional: true,
|
|
259
|
+
description: 'Current burn rate',
|
|
260
|
+
},
|
|
261
|
+
|
|
262
|
+
// Current State
|
|
263
|
+
currentValue: {
|
|
264
|
+
type: 'number',
|
|
265
|
+
optional: true,
|
|
266
|
+
description: 'Current metric value',
|
|
267
|
+
},
|
|
268
|
+
lastCalculatedAt: {
|
|
269
|
+
type: 'date',
|
|
270
|
+
optional: true,
|
|
271
|
+
description: 'Last calculation time',
|
|
272
|
+
},
|
|
273
|
+
|
|
274
|
+
// Alerting
|
|
275
|
+
alertThreshold: {
|
|
276
|
+
type: 'number',
|
|
277
|
+
optional: true,
|
|
278
|
+
description: 'Alert threshold',
|
|
279
|
+
},
|
|
280
|
+
alertOnBreach: {
|
|
281
|
+
type: 'boolean',
|
|
282
|
+
optional: true,
|
|
283
|
+
description: 'Alert on breach',
|
|
284
|
+
},
|
|
285
|
+
|
|
286
|
+
// Status
|
|
287
|
+
status: {
|
|
288
|
+
type: 'string',
|
|
289
|
+
description: 'SLO status',
|
|
290
|
+
examples: ['healthy', 'at-risk', 'breached', 'disabled'],
|
|
291
|
+
},
|
|
292
|
+
isMet: {
|
|
293
|
+
type: 'boolean',
|
|
294
|
+
optional: true,
|
|
295
|
+
description: 'Currently meeting target',
|
|
296
|
+
},
|
|
297
|
+
},
|
|
298
|
+
|
|
299
|
+
relationships: {
|
|
300
|
+
sla: {
|
|
301
|
+
type: 'SLA',
|
|
302
|
+
required: false,
|
|
303
|
+
description: 'Parent SLA',
|
|
304
|
+
},
|
|
305
|
+
service: {
|
|
306
|
+
type: 'ProductizedService',
|
|
307
|
+
description: 'Service measured',
|
|
308
|
+
},
|
|
309
|
+
alerts: {
|
|
310
|
+
type: 'Alert[]',
|
|
311
|
+
description: 'Related alerts',
|
|
312
|
+
},
|
|
313
|
+
},
|
|
314
|
+
|
|
315
|
+
actions: [
|
|
316
|
+
'create',
|
|
317
|
+
'update',
|
|
318
|
+
'enable',
|
|
319
|
+
'disable',
|
|
320
|
+
'recalculate',
|
|
321
|
+
'alert',
|
|
322
|
+
],
|
|
323
|
+
|
|
324
|
+
events: [
|
|
325
|
+
'created',
|
|
326
|
+
'updated',
|
|
327
|
+
'enabled',
|
|
328
|
+
'disabled',
|
|
329
|
+
'breached',
|
|
330
|
+
'recovered',
|
|
331
|
+
'alertTriggered',
|
|
332
|
+
],
|
|
333
|
+
}
|
|
334
|
+
|
|
335
|
+
// =============================================================================
|
|
336
|
+
// ServiceIncident
|
|
337
|
+
// =============================================================================
|
|
338
|
+
|
|
339
|
+
/**
|
|
340
|
+
* ServiceIncident entity
|
|
341
|
+
*
|
|
342
|
+
* Service incident or outage.
|
|
343
|
+
*/
|
|
344
|
+
export const ServiceIncident: Noun = {
|
|
345
|
+
singular: 'service-incident',
|
|
346
|
+
plural: 'service-incidents',
|
|
347
|
+
description: 'A service incident or outage',
|
|
348
|
+
|
|
349
|
+
properties: {
|
|
350
|
+
// Identity
|
|
351
|
+
id: {
|
|
352
|
+
type: 'string',
|
|
353
|
+
description: 'Incident ID',
|
|
354
|
+
},
|
|
355
|
+
title: {
|
|
356
|
+
type: 'string',
|
|
357
|
+
description: 'Incident title',
|
|
358
|
+
},
|
|
359
|
+
description: {
|
|
360
|
+
type: 'string',
|
|
361
|
+
optional: true,
|
|
362
|
+
description: 'Incident description',
|
|
363
|
+
},
|
|
364
|
+
|
|
365
|
+
// Classification
|
|
366
|
+
severity: {
|
|
367
|
+
type: 'string',
|
|
368
|
+
description: 'Incident severity',
|
|
369
|
+
examples: ['critical', 'major', 'minor', 'warning'],
|
|
370
|
+
},
|
|
371
|
+
type: {
|
|
372
|
+
type: 'string',
|
|
373
|
+
optional: true,
|
|
374
|
+
description: 'Incident type',
|
|
375
|
+
examples: ['outage', 'degradation', 'maintenance', 'security', 'data'],
|
|
376
|
+
},
|
|
377
|
+
category: {
|
|
378
|
+
type: 'string',
|
|
379
|
+
optional: true,
|
|
380
|
+
description: 'Incident category',
|
|
381
|
+
},
|
|
382
|
+
|
|
383
|
+
// Impact
|
|
384
|
+
impactLevel: {
|
|
385
|
+
type: 'string',
|
|
386
|
+
optional: true,
|
|
387
|
+
description: 'Impact level',
|
|
388
|
+
examples: ['none', 'partial', 'major', 'complete'],
|
|
389
|
+
},
|
|
390
|
+
affectedServices: {
|
|
391
|
+
type: 'string',
|
|
392
|
+
array: true,
|
|
393
|
+
optional: true,
|
|
394
|
+
description: 'Affected services',
|
|
395
|
+
},
|
|
396
|
+
affectedCustomers: {
|
|
397
|
+
type: 'number',
|
|
398
|
+
optional: true,
|
|
399
|
+
description: 'Number of affected customers',
|
|
400
|
+
},
|
|
401
|
+
affectedRegions: {
|
|
402
|
+
type: 'string',
|
|
403
|
+
array: true,
|
|
404
|
+
optional: true,
|
|
405
|
+
description: 'Affected regions',
|
|
406
|
+
},
|
|
407
|
+
|
|
408
|
+
// Root Cause
|
|
409
|
+
rootCause: {
|
|
410
|
+
type: 'string',
|
|
411
|
+
optional: true,
|
|
412
|
+
description: 'Root cause',
|
|
413
|
+
},
|
|
414
|
+
rootCauseCategory: {
|
|
415
|
+
type: 'string',
|
|
416
|
+
optional: true,
|
|
417
|
+
description: 'Root cause category',
|
|
418
|
+
examples: ['infrastructure', 'code', 'config', 'dependency', 'external', 'unknown'],
|
|
419
|
+
},
|
|
420
|
+
|
|
421
|
+
// Resolution
|
|
422
|
+
resolution: {
|
|
423
|
+
type: 'string',
|
|
424
|
+
optional: true,
|
|
425
|
+
description: 'Resolution description',
|
|
426
|
+
},
|
|
427
|
+
resolutionSteps: {
|
|
428
|
+
type: 'string',
|
|
429
|
+
array: true,
|
|
430
|
+
optional: true,
|
|
431
|
+
description: 'Resolution steps taken',
|
|
432
|
+
},
|
|
433
|
+
preventionPlan: {
|
|
434
|
+
type: 'string',
|
|
435
|
+
optional: true,
|
|
436
|
+
description: 'Prevention plan',
|
|
437
|
+
},
|
|
438
|
+
|
|
439
|
+
// Timeline
|
|
440
|
+
detectedAt: {
|
|
441
|
+
type: 'date',
|
|
442
|
+
optional: true,
|
|
443
|
+
description: 'Detection time',
|
|
444
|
+
},
|
|
445
|
+
startedAt: {
|
|
446
|
+
type: 'date',
|
|
447
|
+
optional: true,
|
|
448
|
+
description: 'Incident start time',
|
|
449
|
+
},
|
|
450
|
+
acknowledgedAt: {
|
|
451
|
+
type: 'date',
|
|
452
|
+
optional: true,
|
|
453
|
+
description: 'Acknowledgement time',
|
|
454
|
+
},
|
|
455
|
+
mitigatedAt: {
|
|
456
|
+
type: 'date',
|
|
457
|
+
optional: true,
|
|
458
|
+
description: 'Mitigation time',
|
|
459
|
+
},
|
|
460
|
+
resolvedAt: {
|
|
461
|
+
type: 'date',
|
|
462
|
+
optional: true,
|
|
463
|
+
description: 'Resolution time',
|
|
464
|
+
},
|
|
465
|
+
closedAt: {
|
|
466
|
+
type: 'date',
|
|
467
|
+
optional: true,
|
|
468
|
+
description: 'Closure time',
|
|
469
|
+
},
|
|
470
|
+
|
|
471
|
+
// Duration
|
|
472
|
+
durationMinutes: {
|
|
473
|
+
type: 'number',
|
|
474
|
+
optional: true,
|
|
475
|
+
description: 'Total duration in minutes',
|
|
476
|
+
},
|
|
477
|
+
timeToDetect: {
|
|
478
|
+
type: 'number',
|
|
479
|
+
optional: true,
|
|
480
|
+
description: 'Time to detect (minutes)',
|
|
481
|
+
},
|
|
482
|
+
timeToMitigate: {
|
|
483
|
+
type: 'number',
|
|
484
|
+
optional: true,
|
|
485
|
+
description: 'Time to mitigate (minutes)',
|
|
486
|
+
},
|
|
487
|
+
timeToResolve: {
|
|
488
|
+
type: 'number',
|
|
489
|
+
optional: true,
|
|
490
|
+
description: 'Time to resolve (minutes)',
|
|
491
|
+
},
|
|
492
|
+
|
|
493
|
+
// Status
|
|
494
|
+
status: {
|
|
495
|
+
type: 'string',
|
|
496
|
+
description: 'Incident status',
|
|
497
|
+
examples: ['detected', 'investigating', 'identified', 'mitigating', 'monitoring', 'resolved', 'closed'],
|
|
498
|
+
},
|
|
499
|
+
isPublic: {
|
|
500
|
+
type: 'boolean',
|
|
501
|
+
optional: true,
|
|
502
|
+
description: 'Visible on status page',
|
|
503
|
+
},
|
|
504
|
+
},
|
|
505
|
+
|
|
506
|
+
relationships: {
|
|
507
|
+
service: {
|
|
508
|
+
type: 'ProductizedService',
|
|
509
|
+
description: 'Affected service',
|
|
510
|
+
},
|
|
511
|
+
sla: {
|
|
512
|
+
type: 'SLA',
|
|
513
|
+
required: false,
|
|
514
|
+
description: 'Related SLA',
|
|
515
|
+
},
|
|
516
|
+
assignee: {
|
|
517
|
+
type: 'Worker',
|
|
518
|
+
required: false,
|
|
519
|
+
description: 'Assigned responder',
|
|
520
|
+
},
|
|
521
|
+
tickets: {
|
|
522
|
+
type: 'SupportTicket[]',
|
|
523
|
+
description: 'Related tickets',
|
|
524
|
+
},
|
|
525
|
+
},
|
|
526
|
+
|
|
527
|
+
actions: [
|
|
528
|
+
'create',
|
|
529
|
+
'acknowledge',
|
|
530
|
+
'investigate',
|
|
531
|
+
'mitigate',
|
|
532
|
+
'resolve',
|
|
533
|
+
'close',
|
|
534
|
+
'reopen',
|
|
535
|
+
'escalate',
|
|
536
|
+
],
|
|
537
|
+
|
|
538
|
+
events: [
|
|
539
|
+
'created',
|
|
540
|
+
'acknowledged',
|
|
541
|
+
'investigating',
|
|
542
|
+
'identified',
|
|
543
|
+
'mitigating',
|
|
544
|
+
'resolved',
|
|
545
|
+
'closed',
|
|
546
|
+
'reopened',
|
|
547
|
+
'escalated',
|
|
548
|
+
],
|
|
549
|
+
}
|
|
550
|
+
|
|
551
|
+
// =============================================================================
|
|
552
|
+
// SupportTicket
|
|
553
|
+
// =============================================================================
|
|
554
|
+
|
|
555
|
+
/**
|
|
556
|
+
* SupportTicket entity
|
|
557
|
+
*
|
|
558
|
+
* Customer support ticket.
|
|
559
|
+
*/
|
|
560
|
+
export const SupportTicket: Noun = {
|
|
561
|
+
singular: 'support-ticket',
|
|
562
|
+
plural: 'support-tickets',
|
|
563
|
+
description: 'A customer support ticket',
|
|
564
|
+
|
|
565
|
+
properties: {
|
|
566
|
+
// Identity
|
|
567
|
+
id: {
|
|
568
|
+
type: 'string',
|
|
569
|
+
description: 'Ticket ID',
|
|
570
|
+
},
|
|
571
|
+
number: {
|
|
572
|
+
type: 'string',
|
|
573
|
+
optional: true,
|
|
574
|
+
description: 'Ticket number',
|
|
575
|
+
},
|
|
576
|
+
|
|
577
|
+
// Content
|
|
578
|
+
subject: {
|
|
579
|
+
type: 'string',
|
|
580
|
+
description: 'Ticket subject',
|
|
581
|
+
},
|
|
582
|
+
description: {
|
|
583
|
+
type: 'string',
|
|
584
|
+
optional: true,
|
|
585
|
+
description: 'Ticket description',
|
|
586
|
+
},
|
|
587
|
+
tags: {
|
|
588
|
+
type: 'string',
|
|
589
|
+
array: true,
|
|
590
|
+
optional: true,
|
|
591
|
+
description: 'Ticket tags',
|
|
592
|
+
},
|
|
593
|
+
|
|
594
|
+
// Classification
|
|
595
|
+
type: {
|
|
596
|
+
type: 'string',
|
|
597
|
+
description: 'Ticket type',
|
|
598
|
+
examples: ['question', 'problem', 'feature-request', 'bug', 'task'],
|
|
599
|
+
},
|
|
600
|
+
category: {
|
|
601
|
+
type: 'string',
|
|
602
|
+
optional: true,
|
|
603
|
+
description: 'Ticket category',
|
|
604
|
+
},
|
|
605
|
+
|
|
606
|
+
// Priority
|
|
607
|
+
priority: {
|
|
608
|
+
type: 'string',
|
|
609
|
+
description: 'Ticket priority',
|
|
610
|
+
examples: ['low', 'normal', 'high', 'urgent'],
|
|
611
|
+
},
|
|
612
|
+
severity: {
|
|
613
|
+
type: 'string',
|
|
614
|
+
optional: true,
|
|
615
|
+
description: 'Issue severity',
|
|
616
|
+
examples: ['cosmetic', 'minor', 'major', 'critical'],
|
|
617
|
+
},
|
|
618
|
+
|
|
619
|
+
// Channel
|
|
620
|
+
channel: {
|
|
621
|
+
type: 'string',
|
|
622
|
+
optional: true,
|
|
623
|
+
description: 'Ticket channel',
|
|
624
|
+
examples: ['email', 'chat', 'phone', 'web', 'api', 'social'],
|
|
625
|
+
},
|
|
626
|
+
|
|
627
|
+
// Assignment
|
|
628
|
+
assignedTo: {
|
|
629
|
+
type: 'string',
|
|
630
|
+
optional: true,
|
|
631
|
+
description: 'Assigned agent',
|
|
632
|
+
},
|
|
633
|
+
assignedTeam: {
|
|
634
|
+
type: 'string',
|
|
635
|
+
optional: true,
|
|
636
|
+
description: 'Assigned team',
|
|
637
|
+
},
|
|
638
|
+
|
|
639
|
+
// SLA
|
|
640
|
+
slaTarget: {
|
|
641
|
+
type: 'date',
|
|
642
|
+
optional: true,
|
|
643
|
+
description: 'SLA target time',
|
|
644
|
+
},
|
|
645
|
+
slaBreached: {
|
|
646
|
+
type: 'boolean',
|
|
647
|
+
optional: true,
|
|
648
|
+
description: 'SLA was breached',
|
|
649
|
+
},
|
|
650
|
+
firstResponseAt: {
|
|
651
|
+
type: 'date',
|
|
652
|
+
optional: true,
|
|
653
|
+
description: 'First response time',
|
|
654
|
+
},
|
|
655
|
+
|
|
656
|
+
// Resolution
|
|
657
|
+
resolution: {
|
|
658
|
+
type: 'string',
|
|
659
|
+
optional: true,
|
|
660
|
+
description: 'Resolution description',
|
|
661
|
+
},
|
|
662
|
+
resolutionCode: {
|
|
663
|
+
type: 'string',
|
|
664
|
+
optional: true,
|
|
665
|
+
description: 'Resolution code',
|
|
666
|
+
examples: ['solved', 'not-a-bug', 'duplicate', 'wont-fix', 'by-design'],
|
|
667
|
+
},
|
|
668
|
+
|
|
669
|
+
// Timeline
|
|
670
|
+
createdAt: {
|
|
671
|
+
type: 'date',
|
|
672
|
+
optional: true,
|
|
673
|
+
description: 'Creation time',
|
|
674
|
+
},
|
|
675
|
+
updatedAt: {
|
|
676
|
+
type: 'date',
|
|
677
|
+
optional: true,
|
|
678
|
+
description: 'Last update time',
|
|
679
|
+
},
|
|
680
|
+
resolvedAt: {
|
|
681
|
+
type: 'date',
|
|
682
|
+
optional: true,
|
|
683
|
+
description: 'Resolution time',
|
|
684
|
+
},
|
|
685
|
+
closedAt: {
|
|
686
|
+
type: 'date',
|
|
687
|
+
optional: true,
|
|
688
|
+
description: 'Closure time',
|
|
689
|
+
},
|
|
690
|
+
|
|
691
|
+
// AI
|
|
692
|
+
aiHandled: {
|
|
693
|
+
type: 'boolean',
|
|
694
|
+
optional: true,
|
|
695
|
+
description: 'Handled by AI',
|
|
696
|
+
},
|
|
697
|
+
aiSuggestedResolution: {
|
|
698
|
+
type: 'string',
|
|
699
|
+
optional: true,
|
|
700
|
+
description: 'AI suggested resolution',
|
|
701
|
+
},
|
|
702
|
+
aiConfidence: {
|
|
703
|
+
type: 'number',
|
|
704
|
+
optional: true,
|
|
705
|
+
description: 'AI confidence score',
|
|
706
|
+
},
|
|
707
|
+
|
|
708
|
+
// Satisfaction
|
|
709
|
+
satisfactionScore: {
|
|
710
|
+
type: 'number',
|
|
711
|
+
optional: true,
|
|
712
|
+
description: 'Customer satisfaction score',
|
|
713
|
+
},
|
|
714
|
+
satisfactionComment: {
|
|
715
|
+
type: 'string',
|
|
716
|
+
optional: true,
|
|
717
|
+
description: 'Satisfaction comment',
|
|
718
|
+
},
|
|
719
|
+
|
|
720
|
+
// Status
|
|
721
|
+
status: {
|
|
722
|
+
type: 'string',
|
|
723
|
+
description: 'Ticket status',
|
|
724
|
+
examples: ['new', 'open', 'pending', 'on-hold', 'escalated', 'solved', 'closed'],
|
|
725
|
+
},
|
|
726
|
+
},
|
|
727
|
+
|
|
728
|
+
relationships: {
|
|
729
|
+
customer: {
|
|
730
|
+
type: 'ServiceCustomer',
|
|
731
|
+
description: 'Customer',
|
|
732
|
+
},
|
|
733
|
+
service: {
|
|
734
|
+
type: 'ProductizedService',
|
|
735
|
+
required: false,
|
|
736
|
+
description: 'Related service',
|
|
737
|
+
},
|
|
738
|
+
incident: {
|
|
739
|
+
type: 'ServiceIncident',
|
|
740
|
+
required: false,
|
|
741
|
+
description: 'Related incident',
|
|
742
|
+
},
|
|
743
|
+
messages: {
|
|
744
|
+
type: 'TicketMessage[]',
|
|
745
|
+
description: 'Ticket messages',
|
|
746
|
+
},
|
|
747
|
+
},
|
|
748
|
+
|
|
749
|
+
actions: [
|
|
750
|
+
'create',
|
|
751
|
+
'assign',
|
|
752
|
+
'respond',
|
|
753
|
+
'escalate',
|
|
754
|
+
'solve',
|
|
755
|
+
'close',
|
|
756
|
+
'reopen',
|
|
757
|
+
],
|
|
758
|
+
|
|
759
|
+
events: [
|
|
760
|
+
'created',
|
|
761
|
+
'assigned',
|
|
762
|
+
'responded',
|
|
763
|
+
'escalated',
|
|
764
|
+
'solved',
|
|
765
|
+
'closed',
|
|
766
|
+
'reopened',
|
|
767
|
+
'ratedByCustomer',
|
|
768
|
+
],
|
|
769
|
+
}
|
|
770
|
+
|
|
771
|
+
// =============================================================================
|
|
772
|
+
// ServiceFeedback
|
|
773
|
+
// =============================================================================
|
|
774
|
+
|
|
775
|
+
/**
|
|
776
|
+
* ServiceFeedback entity
|
|
777
|
+
*
|
|
778
|
+
* Customer feedback on service.
|
|
779
|
+
*/
|
|
780
|
+
export const ServiceFeedback: Noun = {
|
|
781
|
+
singular: 'service-feedback',
|
|
782
|
+
plural: 'service-feedbacks',
|
|
783
|
+
description: 'Customer feedback on a service',
|
|
784
|
+
|
|
785
|
+
properties: {
|
|
786
|
+
// Identity
|
|
787
|
+
id: {
|
|
788
|
+
type: 'string',
|
|
789
|
+
description: 'Feedback ID',
|
|
790
|
+
},
|
|
791
|
+
|
|
792
|
+
// Rating
|
|
793
|
+
rating: {
|
|
794
|
+
type: 'number',
|
|
795
|
+
optional: true,
|
|
796
|
+
description: 'Rating score (1-5)',
|
|
797
|
+
},
|
|
798
|
+
npsScore: {
|
|
799
|
+
type: 'number',
|
|
800
|
+
optional: true,
|
|
801
|
+
description: 'NPS score (0-10)',
|
|
802
|
+
},
|
|
803
|
+
satisfactionScore: {
|
|
804
|
+
type: 'number',
|
|
805
|
+
optional: true,
|
|
806
|
+
description: 'Satisfaction score (1-5)',
|
|
807
|
+
},
|
|
808
|
+
|
|
809
|
+
// Content
|
|
810
|
+
comment: {
|
|
811
|
+
type: 'string',
|
|
812
|
+
optional: true,
|
|
813
|
+
description: 'Feedback comment',
|
|
814
|
+
},
|
|
815
|
+
highlights: {
|
|
816
|
+
type: 'string',
|
|
817
|
+
array: true,
|
|
818
|
+
optional: true,
|
|
819
|
+
description: 'Positive highlights',
|
|
820
|
+
},
|
|
821
|
+
improvements: {
|
|
822
|
+
type: 'string',
|
|
823
|
+
array: true,
|
|
824
|
+
optional: true,
|
|
825
|
+
description: 'Suggested improvements',
|
|
826
|
+
},
|
|
827
|
+
|
|
828
|
+
// Type
|
|
829
|
+
type: {
|
|
830
|
+
type: 'string',
|
|
831
|
+
description: 'Feedback type',
|
|
832
|
+
examples: ['post-execution', 'periodic', 'exit', 'support', 'spontaneous'],
|
|
833
|
+
},
|
|
834
|
+
trigger: {
|
|
835
|
+
type: 'string',
|
|
836
|
+
optional: true,
|
|
837
|
+
description: 'What triggered feedback request',
|
|
838
|
+
},
|
|
839
|
+
|
|
840
|
+
// Context
|
|
841
|
+
context: {
|
|
842
|
+
type: 'json',
|
|
843
|
+
optional: true,
|
|
844
|
+
description: 'Feedback context',
|
|
845
|
+
},
|
|
846
|
+
|
|
847
|
+
// Sentiment
|
|
848
|
+
sentiment: {
|
|
849
|
+
type: 'string',
|
|
850
|
+
optional: true,
|
|
851
|
+
description: 'Detected sentiment',
|
|
852
|
+
examples: ['positive', 'neutral', 'negative', 'mixed'],
|
|
853
|
+
},
|
|
854
|
+
sentimentScore: {
|
|
855
|
+
type: 'number',
|
|
856
|
+
optional: true,
|
|
857
|
+
description: 'Sentiment score (-1 to 1)',
|
|
858
|
+
},
|
|
859
|
+
|
|
860
|
+
// Follow-up
|
|
861
|
+
requiresFollowUp: {
|
|
862
|
+
type: 'boolean',
|
|
863
|
+
optional: true,
|
|
864
|
+
description: 'Requires follow-up',
|
|
865
|
+
},
|
|
866
|
+
followedUpAt: {
|
|
867
|
+
type: 'date',
|
|
868
|
+
optional: true,
|
|
869
|
+
description: 'Follow-up date',
|
|
870
|
+
},
|
|
871
|
+
|
|
872
|
+
// Dates
|
|
873
|
+
submittedAt: {
|
|
874
|
+
type: 'date',
|
|
875
|
+
optional: true,
|
|
876
|
+
description: 'Submission time',
|
|
877
|
+
},
|
|
878
|
+
|
|
879
|
+
// Status
|
|
880
|
+
status: {
|
|
881
|
+
type: 'string',
|
|
882
|
+
description: 'Feedback status',
|
|
883
|
+
examples: ['submitted', 'reviewed', 'actioned', 'archived'],
|
|
884
|
+
},
|
|
885
|
+
},
|
|
886
|
+
|
|
887
|
+
relationships: {
|
|
888
|
+
customer: {
|
|
889
|
+
type: 'ServiceCustomer',
|
|
890
|
+
description: 'Customer',
|
|
891
|
+
},
|
|
892
|
+
service: {
|
|
893
|
+
type: 'ProductizedService',
|
|
894
|
+
description: 'Service',
|
|
895
|
+
},
|
|
896
|
+
execution: {
|
|
897
|
+
type: 'ServiceExecution',
|
|
898
|
+
required: false,
|
|
899
|
+
description: 'Related execution',
|
|
900
|
+
},
|
|
901
|
+
ticket: {
|
|
902
|
+
type: 'SupportTicket',
|
|
903
|
+
required: false,
|
|
904
|
+
description: 'Related ticket',
|
|
905
|
+
},
|
|
906
|
+
},
|
|
907
|
+
|
|
908
|
+
actions: [
|
|
909
|
+
'submit',
|
|
910
|
+
'review',
|
|
911
|
+
'action',
|
|
912
|
+
'followUp',
|
|
913
|
+
'archive',
|
|
914
|
+
],
|
|
915
|
+
|
|
916
|
+
events: [
|
|
917
|
+
'submitted',
|
|
918
|
+
'reviewed',
|
|
919
|
+
'actioned',
|
|
920
|
+
'followedUp',
|
|
921
|
+
'archived',
|
|
922
|
+
],
|
|
923
|
+
}
|
|
924
|
+
|
|
925
|
+
// =============================================================================
|
|
926
|
+
// ServiceMetric
|
|
927
|
+
// =============================================================================
|
|
928
|
+
|
|
929
|
+
/**
|
|
930
|
+
* ServiceMetric entity
|
|
931
|
+
*
|
|
932
|
+
* Service performance metric.
|
|
933
|
+
*/
|
|
934
|
+
export const ServiceMetric: Noun = {
|
|
935
|
+
singular: 'service-metric',
|
|
936
|
+
plural: 'service-metrics',
|
|
937
|
+
description: 'A service performance metric',
|
|
938
|
+
|
|
939
|
+
properties: {
|
|
940
|
+
// Identity
|
|
941
|
+
name: {
|
|
942
|
+
type: 'string',
|
|
943
|
+
description: 'Metric name',
|
|
944
|
+
},
|
|
945
|
+
description: {
|
|
946
|
+
type: 'string',
|
|
947
|
+
optional: true,
|
|
948
|
+
description: 'Metric description',
|
|
949
|
+
},
|
|
950
|
+
|
|
951
|
+
// Classification
|
|
952
|
+
type: {
|
|
953
|
+
type: 'string',
|
|
954
|
+
description: 'Metric type',
|
|
955
|
+
examples: ['counter', 'gauge', 'histogram', 'summary'],
|
|
956
|
+
},
|
|
957
|
+
category: {
|
|
958
|
+
type: 'string',
|
|
959
|
+
optional: true,
|
|
960
|
+
description: 'Metric category',
|
|
961
|
+
examples: ['performance', 'reliability', 'usage', 'cost', 'quality'],
|
|
962
|
+
},
|
|
963
|
+
|
|
964
|
+
// Value
|
|
965
|
+
value: {
|
|
966
|
+
type: 'number',
|
|
967
|
+
optional: true,
|
|
968
|
+
description: 'Current value',
|
|
969
|
+
},
|
|
970
|
+
unit: {
|
|
971
|
+
type: 'string',
|
|
972
|
+
optional: true,
|
|
973
|
+
description: 'Unit of measure',
|
|
974
|
+
},
|
|
975
|
+
|
|
976
|
+
// Aggregation
|
|
977
|
+
aggregation: {
|
|
978
|
+
type: 'string',
|
|
979
|
+
optional: true,
|
|
980
|
+
description: 'Aggregation method',
|
|
981
|
+
examples: ['sum', 'avg', 'min', 'max', 'p50', 'p95', 'p99', 'count'],
|
|
982
|
+
},
|
|
983
|
+
windowDuration: {
|
|
984
|
+
type: 'string',
|
|
985
|
+
optional: true,
|
|
986
|
+
description: 'Aggregation window',
|
|
987
|
+
},
|
|
988
|
+
|
|
989
|
+
// Dimensions
|
|
990
|
+
dimensions: {
|
|
991
|
+
type: 'json',
|
|
992
|
+
optional: true,
|
|
993
|
+
description: 'Metric dimensions/labels',
|
|
994
|
+
},
|
|
995
|
+
|
|
996
|
+
// Targets
|
|
997
|
+
targetValue: {
|
|
998
|
+
type: 'number',
|
|
999
|
+
optional: true,
|
|
1000
|
+
description: 'Target value',
|
|
1001
|
+
},
|
|
1002
|
+
warningThreshold: {
|
|
1003
|
+
type: 'number',
|
|
1004
|
+
optional: true,
|
|
1005
|
+
description: 'Warning threshold',
|
|
1006
|
+
},
|
|
1007
|
+
criticalThreshold: {
|
|
1008
|
+
type: 'number',
|
|
1009
|
+
optional: true,
|
|
1010
|
+
description: 'Critical threshold',
|
|
1011
|
+
},
|
|
1012
|
+
|
|
1013
|
+
// Trends
|
|
1014
|
+
trend: {
|
|
1015
|
+
type: 'string',
|
|
1016
|
+
optional: true,
|
|
1017
|
+
description: 'Value trend',
|
|
1018
|
+
examples: ['improving', 'stable', 'degrading'],
|
|
1019
|
+
},
|
|
1020
|
+
changePercent: {
|
|
1021
|
+
type: 'number',
|
|
1022
|
+
optional: true,
|
|
1023
|
+
description: 'Change percentage from previous period',
|
|
1024
|
+
},
|
|
1025
|
+
|
|
1026
|
+
// Timestamps
|
|
1027
|
+
lastUpdatedAt: {
|
|
1028
|
+
type: 'date',
|
|
1029
|
+
optional: true,
|
|
1030
|
+
description: 'Last update time',
|
|
1031
|
+
},
|
|
1032
|
+
periodStart: {
|
|
1033
|
+
type: 'date',
|
|
1034
|
+
optional: true,
|
|
1035
|
+
description: 'Period start',
|
|
1036
|
+
},
|
|
1037
|
+
periodEnd: {
|
|
1038
|
+
type: 'date',
|
|
1039
|
+
optional: true,
|
|
1040
|
+
description: 'Period end',
|
|
1041
|
+
},
|
|
1042
|
+
|
|
1043
|
+
// Status
|
|
1044
|
+
status: {
|
|
1045
|
+
type: 'string',
|
|
1046
|
+
description: 'Metric status',
|
|
1047
|
+
examples: ['healthy', 'warning', 'critical', 'unknown'],
|
|
1048
|
+
},
|
|
1049
|
+
},
|
|
1050
|
+
|
|
1051
|
+
relationships: {
|
|
1052
|
+
service: {
|
|
1053
|
+
type: 'ProductizedService',
|
|
1054
|
+
description: 'Service measured',
|
|
1055
|
+
},
|
|
1056
|
+
slo: {
|
|
1057
|
+
type: 'SLO',
|
|
1058
|
+
required: false,
|
|
1059
|
+
description: 'Related SLO',
|
|
1060
|
+
},
|
|
1061
|
+
},
|
|
1062
|
+
|
|
1063
|
+
actions: [
|
|
1064
|
+
'create',
|
|
1065
|
+
'update',
|
|
1066
|
+
'record',
|
|
1067
|
+
'aggregate',
|
|
1068
|
+
'alert',
|
|
1069
|
+
],
|
|
1070
|
+
|
|
1071
|
+
events: [
|
|
1072
|
+
'created',
|
|
1073
|
+
'updated',
|
|
1074
|
+
'recorded',
|
|
1075
|
+
'aggregated',
|
|
1076
|
+
'thresholdExceeded',
|
|
1077
|
+
'recovered',
|
|
1078
|
+
],
|
|
1079
|
+
}
|
|
1080
|
+
|
|
1081
|
+
// =============================================================================
|
|
1082
|
+
// Exports
|
|
1083
|
+
// =============================================================================
|
|
1084
|
+
|
|
1085
|
+
export const OperationsEntities = {
|
|
1086
|
+
SLA,
|
|
1087
|
+
SLO,
|
|
1088
|
+
ServiceIncident,
|
|
1089
|
+
SupportTicket,
|
|
1090
|
+
ServiceFeedback,
|
|
1091
|
+
ServiceMetric,
|
|
1092
|
+
}
|
|
1093
|
+
|
|
1094
|
+
export const OperationsCategories = {
|
|
1095
|
+
agreements: ['SLA', 'SLO'],
|
|
1096
|
+
incidents: ['ServiceIncident'],
|
|
1097
|
+
support: ['SupportTicket', 'ServiceFeedback'],
|
|
1098
|
+
metrics: ['ServiceMetric'],
|
|
1099
|
+
} as const
|