@runium/core 0.0.9 → 0.1.0
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/index.js +593 -0
- package/package.json +11 -23
- package/.eslintrc.json +0 -30
- package/.prettierrc.json +0 -10
- package/README.md +0 -1
- package/src/error.ts +0 -22
- package/src/file.ts +0 -53
- package/src/index.ts +0 -8
- package/src/macros.ts +0 -91
- package/src/project-config.ts +0 -483
- package/src/project-schema.ts +0 -767
- package/src/project.ts +0 -748
- package/src/task.ts +0 -381
- package/src/trigger.ts +0 -170
- package/tsconfig.json +0 -29
- package/types/index.d.ts +0 -510
- package/types/package.json +0 -22
- package/vite.config.ts +0 -123
package/src/project-schema.ts
DELETED
|
@@ -1,767 +0,0 @@
|
|
|
1
|
-
import {
|
|
2
|
-
ProjectActionType,
|
|
3
|
-
ProjectTaskRestartPolicyType,
|
|
4
|
-
ProjectTaskStartMode,
|
|
5
|
-
ProjectTaskType,
|
|
6
|
-
ProjectTriggerType,
|
|
7
|
-
} from './project-config';
|
|
8
|
-
import { TaskStatus } from './task';
|
|
9
|
-
import { RuniumError } from './error';
|
|
10
|
-
|
|
11
|
-
interface ProjectSchema {
|
|
12
|
-
properties: {
|
|
13
|
-
tasks: {
|
|
14
|
-
items: {
|
|
15
|
-
oneOf: { $ref: string }[];
|
|
16
|
-
};
|
|
17
|
-
};
|
|
18
|
-
};
|
|
19
|
-
required?: string[];
|
|
20
|
-
$defs: Record<string, ProjectSchemaTask | ProjectSchemaAction | unknown> & {
|
|
21
|
-
Runium_Action: {
|
|
22
|
-
oneOf: { $ref: string }[];
|
|
23
|
-
};
|
|
24
|
-
Runium_Trigger: {
|
|
25
|
-
oneOf: { $ref: string }[];
|
|
26
|
-
};
|
|
27
|
-
};
|
|
28
|
-
}
|
|
29
|
-
|
|
30
|
-
interface ProjectSchemaTask {
|
|
31
|
-
properties: {
|
|
32
|
-
type: {
|
|
33
|
-
const: string;
|
|
34
|
-
};
|
|
35
|
-
};
|
|
36
|
-
}
|
|
37
|
-
|
|
38
|
-
interface ProjectSchemaAction {
|
|
39
|
-
properties: {
|
|
40
|
-
type: {
|
|
41
|
-
const?: string;
|
|
42
|
-
enum?: string[];
|
|
43
|
-
};
|
|
44
|
-
};
|
|
45
|
-
}
|
|
46
|
-
|
|
47
|
-
export interface ProjectSchemaExtensionProject {
|
|
48
|
-
properties: unknown;
|
|
49
|
-
required?: string[];
|
|
50
|
-
}
|
|
51
|
-
|
|
52
|
-
export interface ProjectSchemaExtensionTask {
|
|
53
|
-
type: string;
|
|
54
|
-
options: unknown;
|
|
55
|
-
}
|
|
56
|
-
|
|
57
|
-
export interface ProjectSchemaExtensionAction {
|
|
58
|
-
type: string;
|
|
59
|
-
payload?: unknown;
|
|
60
|
-
}
|
|
61
|
-
|
|
62
|
-
export interface ProjectSchemaExtensionTrigger {
|
|
63
|
-
type: string;
|
|
64
|
-
payload?: unknown;
|
|
65
|
-
}
|
|
66
|
-
|
|
67
|
-
export interface ProjectSchemaExtension {
|
|
68
|
-
project?: ProjectSchemaExtensionProject;
|
|
69
|
-
tasks?: Record<string, ProjectSchemaExtensionTask>;
|
|
70
|
-
definitions?: Record<string, unknown>;
|
|
71
|
-
actions?: Record<string, ProjectSchemaExtensionAction>;
|
|
72
|
-
triggers?: Record<string, ProjectSchemaExtensionTrigger>;
|
|
73
|
-
}
|
|
74
|
-
|
|
75
|
-
export enum ProjectSchemaErrorCode {
|
|
76
|
-
ACTION_TYPE_ALREADY_USED = 'project-schema-action-type-already-used',
|
|
77
|
-
TASK_TYPE_ALREADY_USED = 'project-schema-task-type-already-used',
|
|
78
|
-
TRIGGER_TYPE_ALREADY_USED = 'project-schema-trigger-type-already-used',
|
|
79
|
-
}
|
|
80
|
-
|
|
81
|
-
export const ID_REGEX = /^[a-zA-Z0-9_-]+$/;
|
|
82
|
-
|
|
83
|
-
/**
|
|
84
|
-
* Task common properties
|
|
85
|
-
*/
|
|
86
|
-
const TASK_COMMON_PROPERTIES = {
|
|
87
|
-
id: {
|
|
88
|
-
type: 'string',
|
|
89
|
-
pattern: ID_REGEX.source,
|
|
90
|
-
},
|
|
91
|
-
name: {
|
|
92
|
-
type: 'string',
|
|
93
|
-
},
|
|
94
|
-
type: {
|
|
95
|
-
type: 'string',
|
|
96
|
-
},
|
|
97
|
-
mode: {
|
|
98
|
-
$ref: '#/$defs/Runium_TaskStartMode',
|
|
99
|
-
},
|
|
100
|
-
dependencies: {
|
|
101
|
-
type: 'array',
|
|
102
|
-
items: {
|
|
103
|
-
$ref: '#/$defs/Runium_TaskDependency',
|
|
104
|
-
},
|
|
105
|
-
},
|
|
106
|
-
handlers: {
|
|
107
|
-
type: 'array',
|
|
108
|
-
items: {
|
|
109
|
-
$ref: '#/$defs/Runium_TaskHandler',
|
|
110
|
-
},
|
|
111
|
-
},
|
|
112
|
-
restart: {
|
|
113
|
-
$ref: '#/$defs/Runium_TaskRestartPolicy',
|
|
114
|
-
},
|
|
115
|
-
};
|
|
116
|
-
|
|
117
|
-
/**
|
|
118
|
-
* Trigger common properties
|
|
119
|
-
*/
|
|
120
|
-
const TRIGGER_COMMON_PROPERTIES = {
|
|
121
|
-
id: {
|
|
122
|
-
type: 'string',
|
|
123
|
-
pattern: ID_REGEX.source,
|
|
124
|
-
},
|
|
125
|
-
action: {
|
|
126
|
-
$ref: '#/$defs/Runium_Action',
|
|
127
|
-
},
|
|
128
|
-
disabled: {
|
|
129
|
-
type: 'boolean',
|
|
130
|
-
},
|
|
131
|
-
};
|
|
132
|
-
|
|
133
|
-
/**
|
|
134
|
-
* Create task schema
|
|
135
|
-
* @param type
|
|
136
|
-
* @param options
|
|
137
|
-
*/
|
|
138
|
-
function createTaskSchema(type: string, options: unknown): object {
|
|
139
|
-
return {
|
|
140
|
-
type: 'object',
|
|
141
|
-
properties: {
|
|
142
|
-
...structuredClone(TASK_COMMON_PROPERTIES),
|
|
143
|
-
type: {
|
|
144
|
-
const: type,
|
|
145
|
-
},
|
|
146
|
-
options: {
|
|
147
|
-
...structuredClone(options as object),
|
|
148
|
-
},
|
|
149
|
-
},
|
|
150
|
-
required: ['id', 'options'],
|
|
151
|
-
additionalProperties: false,
|
|
152
|
-
};
|
|
153
|
-
}
|
|
154
|
-
|
|
155
|
-
/**
|
|
156
|
-
* Create action schema
|
|
157
|
-
* @param type
|
|
158
|
-
* @param payload
|
|
159
|
-
*/
|
|
160
|
-
function createActionSchema(type: string, payload?: unknown): object {
|
|
161
|
-
const payloadProp = payload ? { payload } : {};
|
|
162
|
-
const payloadRequired = payload ? ['payload'] : [];
|
|
163
|
-
return {
|
|
164
|
-
type: 'object',
|
|
165
|
-
properties: {
|
|
166
|
-
type: {
|
|
167
|
-
type: 'string',
|
|
168
|
-
const: type,
|
|
169
|
-
},
|
|
170
|
-
...payloadProp,
|
|
171
|
-
},
|
|
172
|
-
required: ['type', ...payloadRequired],
|
|
173
|
-
additionalProperties: false,
|
|
174
|
-
};
|
|
175
|
-
}
|
|
176
|
-
|
|
177
|
-
/**
|
|
178
|
-
* Create trigger schema
|
|
179
|
-
* @param type
|
|
180
|
-
* @param payload
|
|
181
|
-
*/
|
|
182
|
-
function createTriggerSchema(type: string, payload?: unknown): object {
|
|
183
|
-
const payloadProp = payload ? { payload } : {};
|
|
184
|
-
const payloadRequired = payload ? ['payload'] : [];
|
|
185
|
-
return {
|
|
186
|
-
type: 'object',
|
|
187
|
-
properties: {
|
|
188
|
-
...structuredClone(TRIGGER_COMMON_PROPERTIES),
|
|
189
|
-
type: {
|
|
190
|
-
type: 'string',
|
|
191
|
-
const: type,
|
|
192
|
-
},
|
|
193
|
-
...payloadProp,
|
|
194
|
-
},
|
|
195
|
-
required: ['id', 'type', 'action', ...payloadRequired],
|
|
196
|
-
additionalProperties: false,
|
|
197
|
-
};
|
|
198
|
-
}
|
|
199
|
-
|
|
200
|
-
/**
|
|
201
|
-
* Get project schema
|
|
202
|
-
*/
|
|
203
|
-
export function getProjectSchema(): object {
|
|
204
|
-
const schema = {
|
|
205
|
-
$schema: 'https://json-schema.org/draft/2020-12/schema',
|
|
206
|
-
$id: 'https://example.com/schemas/project.json',
|
|
207
|
-
title: 'Project',
|
|
208
|
-
type: 'object',
|
|
209
|
-
properties: {
|
|
210
|
-
id: {
|
|
211
|
-
type: 'string',
|
|
212
|
-
pattern: ID_REGEX.source,
|
|
213
|
-
},
|
|
214
|
-
name: {
|
|
215
|
-
type: 'string',
|
|
216
|
-
},
|
|
217
|
-
tasks: {
|
|
218
|
-
type: 'array',
|
|
219
|
-
items: {
|
|
220
|
-
oneOf: [
|
|
221
|
-
{
|
|
222
|
-
$ref: '#/$defs/Runium_TaskConfig',
|
|
223
|
-
},
|
|
224
|
-
],
|
|
225
|
-
},
|
|
226
|
-
minItems: 1,
|
|
227
|
-
uniqueItemProperties: ['id'],
|
|
228
|
-
},
|
|
229
|
-
triggers: {
|
|
230
|
-
type: 'array',
|
|
231
|
-
items: {
|
|
232
|
-
$ref: '#/$defs/Runium_Trigger',
|
|
233
|
-
},
|
|
234
|
-
uniqueItemProperties: ['id'],
|
|
235
|
-
},
|
|
236
|
-
},
|
|
237
|
-
required: ['id', 'tasks'],
|
|
238
|
-
additionalProperties: false,
|
|
239
|
-
$defs: {
|
|
240
|
-
Runium_EnvValue: {
|
|
241
|
-
type: ['string', 'number', 'boolean'],
|
|
242
|
-
},
|
|
243
|
-
Runium_Env: {
|
|
244
|
-
type: 'object',
|
|
245
|
-
additionalProperties: {
|
|
246
|
-
$ref: '#/$defs/Runium_EnvValue',
|
|
247
|
-
},
|
|
248
|
-
},
|
|
249
|
-
Runium_TaskStartMode: {
|
|
250
|
-
type: 'string',
|
|
251
|
-
enum: Object.values(ProjectTaskStartMode),
|
|
252
|
-
},
|
|
253
|
-
Runium_TaskHandler: {
|
|
254
|
-
type: 'object',
|
|
255
|
-
properties: {
|
|
256
|
-
action: {
|
|
257
|
-
$ref: '#/$defs/Runium_Action',
|
|
258
|
-
},
|
|
259
|
-
condition: {
|
|
260
|
-
$ref: '#/$defs/Runium_TaskStateCondition',
|
|
261
|
-
},
|
|
262
|
-
},
|
|
263
|
-
required: ['action', 'condition'],
|
|
264
|
-
additionalProperties: false,
|
|
265
|
-
},
|
|
266
|
-
Runium_TaskStateCondition: {
|
|
267
|
-
oneOf: [
|
|
268
|
-
{
|
|
269
|
-
type: 'string',
|
|
270
|
-
},
|
|
271
|
-
{
|
|
272
|
-
type: 'boolean',
|
|
273
|
-
},
|
|
274
|
-
{
|
|
275
|
-
$ref: '#/$defs/Runium_TaskState',
|
|
276
|
-
},
|
|
277
|
-
],
|
|
278
|
-
},
|
|
279
|
-
Runium_TaskState: {
|
|
280
|
-
type: 'object',
|
|
281
|
-
properties: {
|
|
282
|
-
status: {
|
|
283
|
-
$ref: '#/$defs/Runium_TaskStatus',
|
|
284
|
-
},
|
|
285
|
-
iteration: {
|
|
286
|
-
type: 'number',
|
|
287
|
-
minimum: 0,
|
|
288
|
-
},
|
|
289
|
-
exitCode: {
|
|
290
|
-
type: 'number',
|
|
291
|
-
minimum: 0,
|
|
292
|
-
},
|
|
293
|
-
reason: {
|
|
294
|
-
type: 'string',
|
|
295
|
-
},
|
|
296
|
-
},
|
|
297
|
-
additionalProperties: false,
|
|
298
|
-
},
|
|
299
|
-
Runium_TaskStatus: {
|
|
300
|
-
type: 'string',
|
|
301
|
-
enum: Object.values(TaskStatus),
|
|
302
|
-
},
|
|
303
|
-
Runium_TaskDependency: {
|
|
304
|
-
type: 'object',
|
|
305
|
-
properties: {
|
|
306
|
-
taskId: {
|
|
307
|
-
type: 'string',
|
|
308
|
-
},
|
|
309
|
-
condition: {
|
|
310
|
-
$ref: '#/$defs/Runium_TaskStateCondition',
|
|
311
|
-
},
|
|
312
|
-
},
|
|
313
|
-
required: ['taskId', 'condition'],
|
|
314
|
-
additionalProperties: false,
|
|
315
|
-
},
|
|
316
|
-
Runium_Trigger: {
|
|
317
|
-
oneOf: [
|
|
318
|
-
{
|
|
319
|
-
$ref: '#/$defs/Runium_TriggerEvent',
|
|
320
|
-
},
|
|
321
|
-
{
|
|
322
|
-
$ref: '#/$defs/Runium_TriggerInterval',
|
|
323
|
-
},
|
|
324
|
-
{
|
|
325
|
-
$ref: '#/$defs/Runium_TriggerTimeout',
|
|
326
|
-
},
|
|
327
|
-
],
|
|
328
|
-
},
|
|
329
|
-
Runium_TriggerEvent: {
|
|
330
|
-
type: 'object',
|
|
331
|
-
properties: {
|
|
332
|
-
...structuredClone(TRIGGER_COMMON_PROPERTIES),
|
|
333
|
-
type: {
|
|
334
|
-
const: ProjectTriggerType.EVENT,
|
|
335
|
-
},
|
|
336
|
-
event: {
|
|
337
|
-
type: 'string',
|
|
338
|
-
},
|
|
339
|
-
},
|
|
340
|
-
required: ['id', 'type', 'event', 'action'],
|
|
341
|
-
additionalProperties: false,
|
|
342
|
-
},
|
|
343
|
-
Runium_TriggerInterval: {
|
|
344
|
-
type: 'object',
|
|
345
|
-
properties: {
|
|
346
|
-
...structuredClone(TRIGGER_COMMON_PROPERTIES),
|
|
347
|
-
type: {
|
|
348
|
-
const: ProjectTriggerType.INTERVAL,
|
|
349
|
-
},
|
|
350
|
-
interval: {
|
|
351
|
-
type: 'number',
|
|
352
|
-
minimum: 0,
|
|
353
|
-
},
|
|
354
|
-
},
|
|
355
|
-
required: ['id', 'type', 'interval', 'action'],
|
|
356
|
-
additionalProperties: false,
|
|
357
|
-
},
|
|
358
|
-
Runium_TriggerTimeout: {
|
|
359
|
-
type: 'object',
|
|
360
|
-
properties: {
|
|
361
|
-
...structuredClone(TRIGGER_COMMON_PROPERTIES),
|
|
362
|
-
type: {
|
|
363
|
-
const: ProjectTriggerType.TIMEOUT,
|
|
364
|
-
},
|
|
365
|
-
timeout: {
|
|
366
|
-
type: 'number',
|
|
367
|
-
minimum: 0,
|
|
368
|
-
},
|
|
369
|
-
},
|
|
370
|
-
required: ['id', 'type', 'timeout', 'action'],
|
|
371
|
-
additionalProperties: false,
|
|
372
|
-
},
|
|
373
|
-
Runium_Action: {
|
|
374
|
-
oneOf: [
|
|
375
|
-
{
|
|
376
|
-
$ref: '#/$defs/Runium_ActionEmitEvent',
|
|
377
|
-
},
|
|
378
|
-
{
|
|
379
|
-
$ref: '#/$defs/Runium_ActionProcessTask',
|
|
380
|
-
},
|
|
381
|
-
{
|
|
382
|
-
$ref: '#/$defs/Runium_ActionStopProject',
|
|
383
|
-
},
|
|
384
|
-
{
|
|
385
|
-
$ref: '#/$defs/Runium_ActionToggleTrigger',
|
|
386
|
-
},
|
|
387
|
-
],
|
|
388
|
-
},
|
|
389
|
-
Runium_ActionEmitEvent: {
|
|
390
|
-
type: 'object',
|
|
391
|
-
properties: {
|
|
392
|
-
type: {
|
|
393
|
-
type: 'string',
|
|
394
|
-
const: ProjectActionType.EMIT_EVENT,
|
|
395
|
-
},
|
|
396
|
-
event: {
|
|
397
|
-
type: 'string',
|
|
398
|
-
},
|
|
399
|
-
},
|
|
400
|
-
required: ['type', 'event'],
|
|
401
|
-
additionalProperties: false,
|
|
402
|
-
},
|
|
403
|
-
Runium_ActionProcessTask: {
|
|
404
|
-
type: 'object',
|
|
405
|
-
properties: {
|
|
406
|
-
type: {
|
|
407
|
-
type: 'string',
|
|
408
|
-
enum: [
|
|
409
|
-
ProjectActionType.START_TASK,
|
|
410
|
-
ProjectActionType.RESTART_TASK,
|
|
411
|
-
ProjectActionType.STOP_TASK,
|
|
412
|
-
],
|
|
413
|
-
},
|
|
414
|
-
taskId: {
|
|
415
|
-
type: 'string',
|
|
416
|
-
},
|
|
417
|
-
},
|
|
418
|
-
required: ['type', 'taskId'],
|
|
419
|
-
additionalProperties: false,
|
|
420
|
-
},
|
|
421
|
-
Runium_ActionStopProject: {
|
|
422
|
-
type: 'object',
|
|
423
|
-
properties: {
|
|
424
|
-
type: {
|
|
425
|
-
type: 'string',
|
|
426
|
-
const: ProjectActionType.STOP_PROJECT,
|
|
427
|
-
},
|
|
428
|
-
},
|
|
429
|
-
required: ['type'],
|
|
430
|
-
additionalProperties: false,
|
|
431
|
-
},
|
|
432
|
-
Runium_ActionToggleTrigger: {
|
|
433
|
-
type: 'object',
|
|
434
|
-
properties: {
|
|
435
|
-
type: {
|
|
436
|
-
type: 'string',
|
|
437
|
-
enum: [
|
|
438
|
-
ProjectActionType.ENABLE_TRIGGER,
|
|
439
|
-
ProjectActionType.DISABLE_TRIGGER,
|
|
440
|
-
],
|
|
441
|
-
},
|
|
442
|
-
triggerId: {
|
|
443
|
-
type: 'string',
|
|
444
|
-
},
|
|
445
|
-
},
|
|
446
|
-
required: ['type', 'triggerId'],
|
|
447
|
-
additionalProperties: false,
|
|
448
|
-
},
|
|
449
|
-
Runium_TaskConfig: {
|
|
450
|
-
...createTaskSchema(ProjectTaskType.DEFAULT, {
|
|
451
|
-
$ref: '#/$defs/Runium_TaskOptions',
|
|
452
|
-
}),
|
|
453
|
-
},
|
|
454
|
-
Runium_TaskOptions: {
|
|
455
|
-
type: 'object',
|
|
456
|
-
properties: {
|
|
457
|
-
command: {
|
|
458
|
-
type: 'string',
|
|
459
|
-
},
|
|
460
|
-
arguments: {
|
|
461
|
-
type: 'array',
|
|
462
|
-
items: {
|
|
463
|
-
type: 'string',
|
|
464
|
-
},
|
|
465
|
-
},
|
|
466
|
-
shell: {
|
|
467
|
-
type: 'boolean',
|
|
468
|
-
},
|
|
469
|
-
cwd: {
|
|
470
|
-
type: 'string',
|
|
471
|
-
},
|
|
472
|
-
env: {
|
|
473
|
-
$ref: '#/$defs/Runium_Env',
|
|
474
|
-
},
|
|
475
|
-
ttl: {
|
|
476
|
-
type: 'number',
|
|
477
|
-
},
|
|
478
|
-
log: {
|
|
479
|
-
$ref: '#/$defs/Runium_TaskLog',
|
|
480
|
-
},
|
|
481
|
-
stopSignal: {
|
|
482
|
-
type: 'string',
|
|
483
|
-
},
|
|
484
|
-
},
|
|
485
|
-
required: ['command'],
|
|
486
|
-
additionalProperties: false,
|
|
487
|
-
},
|
|
488
|
-
Runium_TaskRestartPolicy: {
|
|
489
|
-
oneOf: [
|
|
490
|
-
{
|
|
491
|
-
$ref: '#/$defs/Runium_TaskRestartPolicyAlways',
|
|
492
|
-
},
|
|
493
|
-
{
|
|
494
|
-
$ref: '#/$defs/Runium_TaskRestartPolicyOnFailure',
|
|
495
|
-
},
|
|
496
|
-
],
|
|
497
|
-
},
|
|
498
|
-
Runium_TaskRestartPolicyAlways: {
|
|
499
|
-
type: 'object',
|
|
500
|
-
required: ['policy'],
|
|
501
|
-
properties: {
|
|
502
|
-
policy: {
|
|
503
|
-
const: ProjectTaskRestartPolicyType.ALWAYS,
|
|
504
|
-
},
|
|
505
|
-
delay: {
|
|
506
|
-
type: 'number',
|
|
507
|
-
},
|
|
508
|
-
},
|
|
509
|
-
additionalProperties: false,
|
|
510
|
-
},
|
|
511
|
-
Runium_TaskRestartPolicyOnFailure: {
|
|
512
|
-
type: 'object',
|
|
513
|
-
required: ['policy'],
|
|
514
|
-
properties: {
|
|
515
|
-
policy: {
|
|
516
|
-
const: ProjectTaskRestartPolicyType.ON_FAILURE,
|
|
517
|
-
},
|
|
518
|
-
delay: {
|
|
519
|
-
type: 'number',
|
|
520
|
-
},
|
|
521
|
-
maxRetries: {
|
|
522
|
-
type: 'number',
|
|
523
|
-
},
|
|
524
|
-
},
|
|
525
|
-
additionalProperties: false,
|
|
526
|
-
},
|
|
527
|
-
Runium_TaskLog: {
|
|
528
|
-
type: 'object',
|
|
529
|
-
properties: {
|
|
530
|
-
stdout: {
|
|
531
|
-
type: ['string', 'null'],
|
|
532
|
-
},
|
|
533
|
-
stderr: {
|
|
534
|
-
type: ['string', 'null'],
|
|
535
|
-
},
|
|
536
|
-
},
|
|
537
|
-
additionalProperties: false,
|
|
538
|
-
},
|
|
539
|
-
},
|
|
540
|
-
};
|
|
541
|
-
|
|
542
|
-
return Object.freeze(schema as object);
|
|
543
|
-
}
|
|
544
|
-
|
|
545
|
-
/**
|
|
546
|
-
* Extend project schema
|
|
547
|
-
* @param schema
|
|
548
|
-
* @param extensions
|
|
549
|
-
*/
|
|
550
|
-
export function extendProjectSchema(
|
|
551
|
-
schema: object,
|
|
552
|
-
extensions: ProjectSchemaExtension
|
|
553
|
-
): object {
|
|
554
|
-
let result = structuredClone(schema) as ProjectSchema;
|
|
555
|
-
|
|
556
|
-
// extend project properties
|
|
557
|
-
if (extensions.project) {
|
|
558
|
-
result = extendProjectPropertiesSchema(result, extensions.project);
|
|
559
|
-
}
|
|
560
|
-
|
|
561
|
-
// extend definitions
|
|
562
|
-
if (extensions.definitions) {
|
|
563
|
-
result = extendDefinitionsSchema(result, extensions.definitions);
|
|
564
|
-
}
|
|
565
|
-
|
|
566
|
-
// extend tasks
|
|
567
|
-
if (extensions.tasks) {
|
|
568
|
-
result = extendTasksSchema(result, extensions.tasks);
|
|
569
|
-
}
|
|
570
|
-
|
|
571
|
-
// extend actions
|
|
572
|
-
if (extensions.actions) {
|
|
573
|
-
result = extendActionsSchema(result, extensions.actions);
|
|
574
|
-
}
|
|
575
|
-
|
|
576
|
-
// extend triggers
|
|
577
|
-
if (extensions.triggers) {
|
|
578
|
-
result = extendTriggersSchema(result, extensions.triggers);
|
|
579
|
-
}
|
|
580
|
-
|
|
581
|
-
return Object.freeze(result as object);
|
|
582
|
-
}
|
|
583
|
-
|
|
584
|
-
/**
|
|
585
|
-
* Extend project properties schema
|
|
586
|
-
* @param schema
|
|
587
|
-
* @param extension
|
|
588
|
-
*/
|
|
589
|
-
function extendProjectPropertiesSchema(
|
|
590
|
-
schema: ProjectSchema,
|
|
591
|
-
extension: ProjectSchemaExtension['project']
|
|
592
|
-
): ProjectSchema {
|
|
593
|
-
if (extension) {
|
|
594
|
-
schema.properties = {
|
|
595
|
-
...(extension.properties || {}),
|
|
596
|
-
...schema.properties,
|
|
597
|
-
};
|
|
598
|
-
schema.required = Array.from(
|
|
599
|
-
new Set([...(schema.required ?? []), ...(extension.required ?? [])])
|
|
600
|
-
);
|
|
601
|
-
}
|
|
602
|
-
return schema;
|
|
603
|
-
}
|
|
604
|
-
|
|
605
|
-
/**
|
|
606
|
-
* Extend definitions schema
|
|
607
|
-
* @param schema
|
|
608
|
-
* @param extension
|
|
609
|
-
*/
|
|
610
|
-
function extendDefinitionsSchema(
|
|
611
|
-
schema: ProjectSchema,
|
|
612
|
-
extension: ProjectSchemaExtension['definitions']
|
|
613
|
-
): ProjectSchema {
|
|
614
|
-
if (extension) {
|
|
615
|
-
schema.$defs = {
|
|
616
|
-
...(extension as Record<string, unknown>),
|
|
617
|
-
...schema.$defs,
|
|
618
|
-
};
|
|
619
|
-
}
|
|
620
|
-
return schema;
|
|
621
|
-
}
|
|
622
|
-
|
|
623
|
-
/**
|
|
624
|
-
* Extend tasks schema
|
|
625
|
-
* @param schema
|
|
626
|
-
* @param extension
|
|
627
|
-
*/
|
|
628
|
-
function extendTasksSchema(
|
|
629
|
-
schema: ProjectSchema,
|
|
630
|
-
extension: ProjectSchemaExtension['tasks']
|
|
631
|
-
): ProjectSchema {
|
|
632
|
-
if (extension) {
|
|
633
|
-
// check types uniqueness
|
|
634
|
-
const taskTypes = new Set(
|
|
635
|
-
schema.properties.tasks.items.oneOf.map(task => {
|
|
636
|
-
const taskDef = task.$ref.split('/').pop() || '';
|
|
637
|
-
return (
|
|
638
|
-
(schema.$defs[taskDef] as ProjectSchemaTask)?.properties?.type
|
|
639
|
-
?.const || ProjectTaskType.DEFAULT
|
|
640
|
-
);
|
|
641
|
-
})
|
|
642
|
-
);
|
|
643
|
-
|
|
644
|
-
const tasks: Record<string, object> = {};
|
|
645
|
-
for (const [key, value] of Object.entries(extension)) {
|
|
646
|
-
if (taskTypes.has(value.type)) {
|
|
647
|
-
throw new RuniumError(
|
|
648
|
-
`Task type "${value.type}" already used in project schema`,
|
|
649
|
-
ProjectSchemaErrorCode.TASK_TYPE_ALREADY_USED,
|
|
650
|
-
{
|
|
651
|
-
type: value.type,
|
|
652
|
-
}
|
|
653
|
-
);
|
|
654
|
-
}
|
|
655
|
-
tasks[key] = createTaskSchema(value.type, value.options);
|
|
656
|
-
|
|
657
|
-
schema.properties.tasks.items.oneOf.push({
|
|
658
|
-
$ref: `#/$defs/${key}`,
|
|
659
|
-
});
|
|
660
|
-
|
|
661
|
-
taskTypes.add(value.type);
|
|
662
|
-
}
|
|
663
|
-
schema.$defs = {
|
|
664
|
-
...tasks,
|
|
665
|
-
...schema.$defs,
|
|
666
|
-
};
|
|
667
|
-
}
|
|
668
|
-
return schema;
|
|
669
|
-
}
|
|
670
|
-
|
|
671
|
-
/**
|
|
672
|
-
* Extend actions schema
|
|
673
|
-
* @param schema
|
|
674
|
-
* @param extension
|
|
675
|
-
*/
|
|
676
|
-
function extendActionsSchema(
|
|
677
|
-
schema: ProjectSchema,
|
|
678
|
-
extension: ProjectSchemaExtension['actions']
|
|
679
|
-
): ProjectSchema {
|
|
680
|
-
if (extension) {
|
|
681
|
-
// check types uniqueness
|
|
682
|
-
const actionTypes = new Set(
|
|
683
|
-
schema.$defs.Runium_Action.oneOf
|
|
684
|
-
.map(action => {
|
|
685
|
-
const actionDef = action.$ref.split('/').pop() || '';
|
|
686
|
-
const actionType = (schema.$defs[actionDef] as ProjectSchemaAction)
|
|
687
|
-
?.properties?.type;
|
|
688
|
-
return actionType?.enum || [actionType?.const];
|
|
689
|
-
})
|
|
690
|
-
.flat()
|
|
691
|
-
);
|
|
692
|
-
|
|
693
|
-
const actions: Record<string, object> = {};
|
|
694
|
-
for (const [key, value] of Object.entries(extension)) {
|
|
695
|
-
if (actionTypes.has(value.type)) {
|
|
696
|
-
throw new RuniumError(
|
|
697
|
-
`Action type "${value.type}" already used in project schema`,
|
|
698
|
-
ProjectSchemaErrorCode.ACTION_TYPE_ALREADY_USED,
|
|
699
|
-
{
|
|
700
|
-
type: value.type,
|
|
701
|
-
}
|
|
702
|
-
);
|
|
703
|
-
}
|
|
704
|
-
|
|
705
|
-
actions[key] = createActionSchema(value.type, value.payload);
|
|
706
|
-
|
|
707
|
-
schema.$defs.Runium_Action.oneOf.push({
|
|
708
|
-
$ref: `#/$defs/${key}`,
|
|
709
|
-
});
|
|
710
|
-
|
|
711
|
-
actionTypes.add(value.type);
|
|
712
|
-
}
|
|
713
|
-
schema.$defs = {
|
|
714
|
-
...actions,
|
|
715
|
-
...schema.$defs,
|
|
716
|
-
};
|
|
717
|
-
}
|
|
718
|
-
return schema;
|
|
719
|
-
}
|
|
720
|
-
|
|
721
|
-
/**
|
|
722
|
-
* Extend triggers schema
|
|
723
|
-
* @param schema
|
|
724
|
-
* @param extension
|
|
725
|
-
*/
|
|
726
|
-
function extendTriggersSchema(
|
|
727
|
-
schema: ProjectSchema,
|
|
728
|
-
extension: ProjectSchemaExtension['triggers']
|
|
729
|
-
): ProjectSchema {
|
|
730
|
-
if (extension) {
|
|
731
|
-
// check types uniqueness
|
|
732
|
-
const triggerTypes = new Set(
|
|
733
|
-
schema.$defs.Runium_Trigger.oneOf.map(trigger => {
|
|
734
|
-
const triggerDef = trigger.$ref.split('/').pop() || '';
|
|
735
|
-
const triggerType = (schema.$defs[triggerDef] as ProjectSchemaAction)
|
|
736
|
-
?.properties?.type;
|
|
737
|
-
return triggerType?.const;
|
|
738
|
-
})
|
|
739
|
-
);
|
|
740
|
-
|
|
741
|
-
const triggers: Record<string, object> = {};
|
|
742
|
-
for (const [key, value] of Object.entries(extension)) {
|
|
743
|
-
if (triggerTypes.has(value.type)) {
|
|
744
|
-
throw new RuniumError(
|
|
745
|
-
`Trigger type "${value.type}" already used in project schema`,
|
|
746
|
-
ProjectSchemaErrorCode.TRIGGER_TYPE_ALREADY_USED,
|
|
747
|
-
{
|
|
748
|
-
type: value.type,
|
|
749
|
-
}
|
|
750
|
-
);
|
|
751
|
-
}
|
|
752
|
-
|
|
753
|
-
triggers[key] = createTriggerSchema(value.type, value.payload);
|
|
754
|
-
|
|
755
|
-
schema.$defs.Runium_Trigger.oneOf.push({
|
|
756
|
-
$ref: `#/$defs/${key}`,
|
|
757
|
-
});
|
|
758
|
-
|
|
759
|
-
triggerTypes.add(value.type);
|
|
760
|
-
}
|
|
761
|
-
schema.$defs = {
|
|
762
|
-
...triggers,
|
|
763
|
-
...schema.$defs,
|
|
764
|
-
};
|
|
765
|
-
}
|
|
766
|
-
return schema;
|
|
767
|
-
}
|