@usehelical/workflows 0.0.1-alpha.13 → 0.0.1-alpha.15
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/dist/{chunk-SQ7WUJCB.js → chunk-TZSPUZQ3.js} +275 -169
- package/dist/chunk-TZSPUZQ3.js.map +1 -0
- package/dist/index.d.ts +1 -9
- package/dist/index.js +99 -113
- package/dist/index.js.map +1 -1
- package/dist/{run-oOlOK2Rg.d.ts → run-BDlJdILv.d.ts} +18 -2
- package/dist/workflows.d.ts +11 -3
- package/dist/workflows.js +114 -28
- package/dist/workflows.js.map +1 -1
- package/package.json +1 -1
- package/dist/chunk-SQ7WUJCB.js.map +0 -1
|
@@ -28,95 +28,29 @@ var QueueNotFoundError = class extends Error {
|
|
|
28
28
|
}
|
|
29
29
|
};
|
|
30
30
|
|
|
31
|
-
// core/
|
|
32
|
-
var
|
|
33
|
-
|
|
34
|
-
|
|
35
|
-
|
|
36
|
-
|
|
37
|
-
|
|
38
|
-
|
|
39
|
-
|
|
40
|
-
|
|
41
|
-
|
|
42
|
-
|
|
43
|
-
};
|
|
44
|
-
|
|
45
|
-
constructor() {
|
|
46
|
-
super("This function must be called within a workflow");
|
|
47
|
-
this.name = "RUN_OUTSIDE_OF_WORKFLOW" /* RUN_OUTSIDE_OF_WORKFLOW */;
|
|
48
|
-
}
|
|
49
|
-
};
|
|
50
|
-
var FatalError = class extends Error {
|
|
51
|
-
constructor(message) {
|
|
52
|
-
super(message);
|
|
53
|
-
this.name = "FATAL_ERROR" /* FATAL_ERROR */;
|
|
54
|
-
}
|
|
55
|
-
};
|
|
56
|
-
var MaxRetriesExceededError = class extends Error {
|
|
57
|
-
attemptErrors;
|
|
58
|
-
stepName;
|
|
59
|
-
maxAttempts;
|
|
60
|
-
constructor(stepName, maxAttempts, errors) {
|
|
61
|
-
const formattedErrors = errors.map((error, index) => `Attempt ${index + 1}: ${error.message}`).join(". ");
|
|
62
|
-
super(`Step "${stepName}" failed after ${maxAttempts + 1} attempts. ${formattedErrors}`);
|
|
63
|
-
this.name = "MAX_RETRIES_EXCEEDED" /* MAX_RETRIES_EXCEEDED */;
|
|
64
|
-
this.attemptErrors = errors;
|
|
65
|
-
this.stepName = stepName;
|
|
66
|
-
this.maxAttempts = maxAttempts;
|
|
67
|
-
}
|
|
68
|
-
};
|
|
69
|
-
var ErrorThatShouldNeverHappen = class extends Error {
|
|
70
|
-
constructor(message) {
|
|
71
|
-
super(message);
|
|
72
|
-
this.name = "ERROR_THAT_SHOULD_NEVER_HAPPEN" /* ERROR_THAT_SHOULD_NEVER_HAPPEN */;
|
|
73
|
-
}
|
|
74
|
-
};
|
|
75
|
-
var SerializationError = class extends Error {
|
|
76
|
-
constructor(message) {
|
|
77
|
-
super(message);
|
|
78
|
-
this.name = "SERIALIZATION_ERROR" /* SERIALIZATION_ERROR */;
|
|
79
|
-
}
|
|
80
|
-
};
|
|
81
|
-
var TimeoutError2 = class extends Error {
|
|
82
|
-
constructor(message) {
|
|
83
|
-
super(message);
|
|
84
|
-
this.name = "TIMEOUT" /* TIMEOUT */;
|
|
85
|
-
}
|
|
86
|
-
};
|
|
87
|
-
var DeadlineError = class extends Error {
|
|
88
|
-
constructor(message) {
|
|
89
|
-
super(message);
|
|
90
|
-
this.name = "DEADLINE" /* DEADLINE */;
|
|
91
|
-
}
|
|
92
|
-
};
|
|
93
|
-
function serialize(value) {
|
|
94
|
-
try {
|
|
95
|
-
return JSON.stringify(value);
|
|
96
|
-
} catch (error) {
|
|
97
|
-
throw new SerializationError(error.message);
|
|
98
|
-
}
|
|
99
|
-
}
|
|
100
|
-
function deserialize(value) {
|
|
101
|
-
try {
|
|
102
|
-
return JSON.parse(value);
|
|
103
|
-
} catch (error) {
|
|
104
|
-
throw new SerializationError(error.message);
|
|
105
|
-
}
|
|
106
|
-
}
|
|
107
|
-
function serializeError(error) {
|
|
108
|
-
try {
|
|
109
|
-
return JSON.stringify(serializeError$1(error));
|
|
110
|
-
} catch (error2) {
|
|
111
|
-
throw new SerializationError(error2.message);
|
|
112
|
-
}
|
|
31
|
+
// core/workflow.ts
|
|
32
|
+
var TERMINAL_STATES = [
|
|
33
|
+
"success",
|
|
34
|
+
"error",
|
|
35
|
+
"cancelled",
|
|
36
|
+
"max_recovery_attempts_exceeded"
|
|
37
|
+
];
|
|
38
|
+
function defineWorkflow(fn, options = {}) {
|
|
39
|
+
return () => {
|
|
40
|
+
return {
|
|
41
|
+
fn,
|
|
42
|
+
maxRecoveryAttempts: options.maxRecoveryAttempts
|
|
43
|
+
};
|
|
44
|
+
};
|
|
113
45
|
}
|
|
114
|
-
|
|
115
|
-
|
|
116
|
-
|
|
117
|
-
|
|
118
|
-
|
|
46
|
+
|
|
47
|
+
// core/internal/repository/get-state.ts
|
|
48
|
+
async function getState(db, runId, key) {
|
|
49
|
+
const result = await db.selectFrom("state").select(["key", "value", "change_id"]).where("run_id", "=", runId).where("key", "=", key).executeTakeFirst();
|
|
50
|
+
if (!result) {
|
|
51
|
+
return void 0;
|
|
119
52
|
}
|
|
53
|
+
return result.value;
|
|
120
54
|
}
|
|
121
55
|
|
|
122
56
|
// core/internal/utils/sleep.ts
|
|
@@ -234,6 +168,116 @@ async function withDbRetry(fn, options = {}) {
|
|
|
234
168
|
}
|
|
235
169
|
}
|
|
236
170
|
}
|
|
171
|
+
|
|
172
|
+
// core/internal/errors.ts
|
|
173
|
+
var BaseError = class extends Error {
|
|
174
|
+
reason;
|
|
175
|
+
constructor(message, reason) {
|
|
176
|
+
super(message);
|
|
177
|
+
this.reason = reason;
|
|
178
|
+
}
|
|
179
|
+
};
|
|
180
|
+
var RunTimedOutError = class extends BaseError {
|
|
181
|
+
constructor() {
|
|
182
|
+
super("This workflow run has timed out", "timeout");
|
|
183
|
+
}
|
|
184
|
+
};
|
|
185
|
+
var UnknownError = class extends BaseError {
|
|
186
|
+
constructor(message) {
|
|
187
|
+
super(message || "An unknown error occurred", "unknown");
|
|
188
|
+
}
|
|
189
|
+
};
|
|
190
|
+
var RunDeadlineExceededError = class extends BaseError {
|
|
191
|
+
constructor() {
|
|
192
|
+
super("This workflow run has exceeded its deadline", "deadline");
|
|
193
|
+
}
|
|
194
|
+
};
|
|
195
|
+
var RunCancelledError = class extends BaseError {
|
|
196
|
+
constructor(message) {
|
|
197
|
+
super(message || "This workflow run has been cancelled", "cancel");
|
|
198
|
+
}
|
|
199
|
+
};
|
|
200
|
+
var MaxRecoveryAttemptsExceededError2 = class extends BaseError {
|
|
201
|
+
constructor(message) {
|
|
202
|
+
super(message || "Max recovery attempts exceeded", "max_recovery_attempts_exceeded");
|
|
203
|
+
}
|
|
204
|
+
};
|
|
205
|
+
var OperationTimedOutError = class extends BaseError {
|
|
206
|
+
constructor(operationName) {
|
|
207
|
+
super(`This operation "${operationName}" has timed out`, "timeout");
|
|
208
|
+
}
|
|
209
|
+
};
|
|
210
|
+
var RunNotFoundError = class extends Error {
|
|
211
|
+
constructor(runId) {
|
|
212
|
+
super(`Workflow run "${runId}" not found`);
|
|
213
|
+
this.name = "RUN_NOT_FOUND" /* RUN_NOT_FOUND */;
|
|
214
|
+
}
|
|
215
|
+
};
|
|
216
|
+
var RunOutsideOfWorkflowError = class extends Error {
|
|
217
|
+
constructor() {
|
|
218
|
+
super("This function must be called within a workflow");
|
|
219
|
+
this.name = "RUN_OUTSIDE_OF_WORKFLOW" /* RUN_OUTSIDE_OF_WORKFLOW */;
|
|
220
|
+
}
|
|
221
|
+
};
|
|
222
|
+
var FatalError = class extends Error {
|
|
223
|
+
constructor(message) {
|
|
224
|
+
super(message);
|
|
225
|
+
this.name = "FATAL_ERROR" /* FATAL_ERROR */;
|
|
226
|
+
}
|
|
227
|
+
};
|
|
228
|
+
var MaxRetriesExceededError = class extends Error {
|
|
229
|
+
attemptErrors;
|
|
230
|
+
stepName;
|
|
231
|
+
maxAttempts;
|
|
232
|
+
constructor(stepName, maxAttempts, errors) {
|
|
233
|
+
const formattedErrors = errors.map((error, index) => `Attempt ${index + 1}: ${error.message}`).join(". ");
|
|
234
|
+
super(`Step "${stepName}" failed after ${maxAttempts + 1} attempts. ${formattedErrors}`);
|
|
235
|
+
this.name = "MAX_RETRIES_EXCEEDED" /* MAX_RETRIES_EXCEEDED */;
|
|
236
|
+
this.attemptErrors = errors;
|
|
237
|
+
this.stepName = stepName;
|
|
238
|
+
this.maxAttempts = maxAttempts;
|
|
239
|
+
}
|
|
240
|
+
};
|
|
241
|
+
var ErrorThatShouldNeverHappen = class extends Error {
|
|
242
|
+
constructor(message) {
|
|
243
|
+
super(message);
|
|
244
|
+
this.name = "ERROR_THAT_SHOULD_NEVER_HAPPEN" /* ERROR_THAT_SHOULD_NEVER_HAPPEN */;
|
|
245
|
+
}
|
|
246
|
+
};
|
|
247
|
+
var SerializationError = class extends Error {
|
|
248
|
+
constructor(message) {
|
|
249
|
+
super(message);
|
|
250
|
+
this.name = "SERIALIZATION_ERROR" /* SERIALIZATION_ERROR */;
|
|
251
|
+
}
|
|
252
|
+
};
|
|
253
|
+
function serialize(value) {
|
|
254
|
+
try {
|
|
255
|
+
return JSON.stringify(value);
|
|
256
|
+
} catch (error) {
|
|
257
|
+
throw new SerializationError(error.message);
|
|
258
|
+
}
|
|
259
|
+
}
|
|
260
|
+
function deserialize(value) {
|
|
261
|
+
try {
|
|
262
|
+
return JSON.parse(value);
|
|
263
|
+
} catch (error) {
|
|
264
|
+
throw new SerializationError(error.message);
|
|
265
|
+
}
|
|
266
|
+
}
|
|
267
|
+
function serializeError(error) {
|
|
268
|
+
try {
|
|
269
|
+
return JSON.stringify(serializeError$1(error));
|
|
270
|
+
} catch (error2) {
|
|
271
|
+
throw new SerializationError(error2.message);
|
|
272
|
+
}
|
|
273
|
+
}
|
|
274
|
+
function deserializeError(serialized) {
|
|
275
|
+
try {
|
|
276
|
+
return deserializeError$1(JSON.parse(serialized));
|
|
277
|
+
} catch (error) {
|
|
278
|
+
throw new SerializationError(error.message);
|
|
279
|
+
}
|
|
280
|
+
}
|
|
237
281
|
function getExecutionContext() {
|
|
238
282
|
const store = asyncLocalStorage.getStore();
|
|
239
283
|
if (!store) {
|
|
@@ -273,7 +317,7 @@ async function insertOperation(tx, runId, operationName, sequenceId, result, err
|
|
|
273
317
|
}).execute();
|
|
274
318
|
}
|
|
275
319
|
|
|
276
|
-
// core/internal/operation-manager.ts
|
|
320
|
+
// core/internal/context/operation-manager.ts
|
|
277
321
|
var OperationManager = class {
|
|
278
322
|
constructor(db, runId, operations = []) {
|
|
279
323
|
this.db = db;
|
|
@@ -399,53 +443,22 @@ function createExecutionContext({
|
|
|
399
443
|
db: ctx.db
|
|
400
444
|
};
|
|
401
445
|
}
|
|
402
|
-
async function recordRunResult(db, runId, result) {
|
|
446
|
+
async function recordRunResult(db, runId, result, cancelled) {
|
|
403
447
|
const [{ change_id }] = await db.updateTable("runs").set({
|
|
404
448
|
output: result.result,
|
|
405
449
|
error: result.error,
|
|
406
|
-
status: result.error ? "error" : "success",
|
|
450
|
+
status: cancelled ? "cancelled" : result.error ? "error" : "success",
|
|
407
451
|
updated_at: sql`(extract(epoch from now()) * 1000)::bigint`
|
|
408
452
|
}).where("id", "=", runId).returning(["change_id"]).execute();
|
|
409
453
|
return change_id;
|
|
410
454
|
}
|
|
411
|
-
async function cancelRun(runId, db) {
|
|
412
|
-
return withDbRetry(async () => {
|
|
413
|
-
return db.transaction().execute(async (tx) => {
|
|
414
|
-
const result = await tx.updateTable("runs").set({
|
|
415
|
-
status: "cancelled",
|
|
416
|
-
updated_at: sql`(extract(epoch from now()) * 1000)::bigint`
|
|
417
|
-
}).where(
|
|
418
|
-
(eb) => eb.and([eb("id", "=", runId), eb("status", "not in", ["cancelled", "success", "error"])])
|
|
419
|
-
).returning(["change_id", "path"]).executeTakeFirst();
|
|
420
|
-
if (!result) {
|
|
421
|
-
const exists = await tx.selectFrom("runs").select([]).where("id", "=", runId).executeTakeFirst();
|
|
422
|
-
if (exists) {
|
|
423
|
-
return void 0;
|
|
424
|
-
}
|
|
425
|
-
throw new RunNotFoundError(runId);
|
|
426
|
-
}
|
|
427
|
-
await sql`
|
|
428
|
-
UPDATE runs
|
|
429
|
-
SET
|
|
430
|
-
status = ${"cancelled"},
|
|
431
|
-
updated_at = (extract(epoch from now()) * 1000)::bigint
|
|
432
|
-
WHERE path @> ARRAY[${runId}]::text[]
|
|
433
|
-
AND id != ${runId}
|
|
434
|
-
AND status NOT IN (${"cancelled"}, ${"success"}, ${"error"})
|
|
435
|
-
`.execute(tx);
|
|
436
|
-
return {
|
|
437
|
-
path: result.path
|
|
438
|
-
};
|
|
439
|
-
});
|
|
440
|
-
});
|
|
441
|
-
}
|
|
442
455
|
|
|
443
456
|
// core/internal/execute-workflow.ts
|
|
444
457
|
async function executeWorkflow(ctx, params) {
|
|
445
458
|
const { db, runRegistry } = ctx;
|
|
446
459
|
const { options, runId, runPath, fn, args, operations } = params;
|
|
447
460
|
const abortController = new AbortController();
|
|
448
|
-
const [deadline] = getDeadlineAndReason({
|
|
461
|
+
const [deadline, deadlineReason] = getDeadlineAndReason({
|
|
449
462
|
timeout: options?.timeout,
|
|
450
463
|
deadline: options?.deadline
|
|
451
464
|
});
|
|
@@ -463,12 +476,16 @@ async function executeWorkflow(ctx, params) {
|
|
|
463
476
|
const result = await runWithExecutionContext(runStore, async () => {
|
|
464
477
|
return await runWithTimeout(async () => {
|
|
465
478
|
return await fn(...args);
|
|
466
|
-
});
|
|
479
|
+
}, deadlineReason);
|
|
467
480
|
});
|
|
468
481
|
await recordRunResult(db, runId, { result: result ? serialize(result) : void 0 });
|
|
469
482
|
return result;
|
|
470
483
|
} catch (error) {
|
|
471
|
-
|
|
484
|
+
if (error instanceof RunCancelledError) {
|
|
485
|
+
await recordRunResult(db, runId, { error: serializeError(error) }, true);
|
|
486
|
+
} else {
|
|
487
|
+
await recordRunResult(db, runId, { error: serializeError(error) });
|
|
488
|
+
}
|
|
472
489
|
throw error;
|
|
473
490
|
} finally {
|
|
474
491
|
runRegistry.unregisterRun(runId);
|
|
@@ -498,15 +515,15 @@ function getDeadlineAndReason({
|
|
|
498
515
|
}
|
|
499
516
|
return [void 0, void 0];
|
|
500
517
|
}
|
|
501
|
-
async function runWithTimeout(fn) {
|
|
502
|
-
const {
|
|
518
|
+
async function runWithTimeout(fn, deadlineReason) {
|
|
519
|
+
const { abortSignal } = getExecutionContext();
|
|
503
520
|
const abortPromise = new Promise((_, reject) => {
|
|
504
521
|
abortSignal.throwIfAborted();
|
|
505
522
|
abortSignal.addEventListener(
|
|
506
523
|
"abort",
|
|
507
524
|
() => {
|
|
508
525
|
if (abortSignal.reason?.name === "TimeoutError") {
|
|
509
|
-
reject(new
|
|
526
|
+
reject(new RunTimedOutError());
|
|
510
527
|
return;
|
|
511
528
|
}
|
|
512
529
|
reject(new RunCancelledError());
|
|
@@ -518,8 +535,13 @@ async function runWithTimeout(fn) {
|
|
|
518
535
|
try {
|
|
519
536
|
return await Promise.race([callPromise, abortPromise]);
|
|
520
537
|
} catch (error) {
|
|
521
|
-
if (error instanceof
|
|
522
|
-
|
|
538
|
+
if (error instanceof RunTimedOutError) {
|
|
539
|
+
if (deadlineReason === "timeout") {
|
|
540
|
+
throw new RunTimedOutError();
|
|
541
|
+
} else if (deadlineReason === "deadline") {
|
|
542
|
+
throw new RunDeadlineExceededError();
|
|
543
|
+
}
|
|
544
|
+
throw error;
|
|
523
545
|
}
|
|
524
546
|
await callPromise.catch(() => {
|
|
525
547
|
});
|
|
@@ -527,7 +549,7 @@ async function runWithTimeout(fn) {
|
|
|
527
549
|
}
|
|
528
550
|
}
|
|
529
551
|
|
|
530
|
-
// core/internal/
|
|
552
|
+
// core/internal/db/queries/get-run-status.ts
|
|
531
553
|
async function getRunStatus(db, runId) {
|
|
532
554
|
const run = await db.selectFrom("runs").select("status").where("id", "=", runId).executeTakeFirst();
|
|
533
555
|
if (!run) {
|
|
@@ -536,16 +558,16 @@ async function getRunStatus(db, runId) {
|
|
|
536
558
|
return run.status;
|
|
537
559
|
}
|
|
538
560
|
|
|
539
|
-
//
|
|
561
|
+
// core/internal/get-run-status.ts
|
|
540
562
|
async function getRunStatus2(ctx, runId) {
|
|
541
563
|
const { db, runRegistry } = ctx;
|
|
542
564
|
const run = runRegistry.getRun(runId);
|
|
543
565
|
if (run) {
|
|
544
|
-
return
|
|
566
|
+
return deriveRunStatus(run);
|
|
545
567
|
}
|
|
546
568
|
return getRunStatus(db, runId);
|
|
547
569
|
}
|
|
548
|
-
async function
|
|
570
|
+
async function deriveRunStatus(runEntry) {
|
|
549
571
|
if (runEntry.store.abortSignal.aborted) {
|
|
550
572
|
return "cancelled";
|
|
551
573
|
}
|
|
@@ -559,7 +581,7 @@ async function getRunStatusFromRegistry(runEntry) {
|
|
|
559
581
|
return "error";
|
|
560
582
|
}
|
|
561
583
|
|
|
562
|
-
//
|
|
584
|
+
// core/internal/wait-for-run-result.ts
|
|
563
585
|
async function waitForRunResult(ctx, runId) {
|
|
564
586
|
const { db, runEventBus } = ctx;
|
|
565
587
|
const run = await getRun(db, runId);
|
|
@@ -569,48 +591,69 @@ async function waitForRunResult(ctx, runId) {
|
|
|
569
591
|
success: false
|
|
570
592
|
};
|
|
571
593
|
}
|
|
572
|
-
|
|
573
|
-
|
|
574
|
-
|
|
575
|
-
|
|
576
|
-
|
|
577
|
-
|
|
578
|
-
|
|
579
|
-
|
|
580
|
-
|
|
581
|
-
|
|
582
|
-
|
|
594
|
+
switch (run.status) {
|
|
595
|
+
case "success":
|
|
596
|
+
return {
|
|
597
|
+
data: run.output ? deserialize(run.output) : void 0,
|
|
598
|
+
success: true
|
|
599
|
+
};
|
|
600
|
+
case "error":
|
|
601
|
+
return {
|
|
602
|
+
error: run.error ? deserializeError(run.error) : new UnknownError(),
|
|
603
|
+
success: false
|
|
604
|
+
};
|
|
605
|
+
case "cancelled":
|
|
606
|
+
return {
|
|
607
|
+
error: new RunCancelledError(),
|
|
608
|
+
success: false
|
|
609
|
+
};
|
|
610
|
+
case "max_recovery_attempts_exceeded":
|
|
611
|
+
return {
|
|
612
|
+
error: run.error ? deserializeError(run.error) : new MaxRecoveryAttemptsExceededError2(),
|
|
613
|
+
success: false
|
|
614
|
+
};
|
|
583
615
|
}
|
|
584
616
|
return new Promise((resolve, reject) => {
|
|
585
617
|
const unsubscribe = runEventBus.subscribe(runId, "*", async (e) => {
|
|
586
|
-
if (e.status
|
|
587
|
-
unsubscribe();
|
|
588
|
-
resolve({
|
|
589
|
-
error: new RunCancelledError(),
|
|
590
|
-
success: false
|
|
591
|
-
});
|
|
592
|
-
return;
|
|
593
|
-
}
|
|
594
|
-
if (e.status === "success" || e.status === "error") {
|
|
618
|
+
if (TERMINAL_STATES.includes(e.status)) {
|
|
595
619
|
unsubscribe();
|
|
596
620
|
try {
|
|
597
|
-
const
|
|
598
|
-
if (!
|
|
621
|
+
const run2 = await getRun(db, runId);
|
|
622
|
+
if (!run2) {
|
|
599
623
|
reject(new RunNotFoundError(runId));
|
|
600
624
|
return;
|
|
601
625
|
}
|
|
602
|
-
|
|
603
|
-
|
|
604
|
-
|
|
605
|
-
|
|
606
|
-
|
|
607
|
-
|
|
626
|
+
switch (run2.status) {
|
|
627
|
+
case "success":
|
|
628
|
+
resolve({
|
|
629
|
+
data: run2.output ? deserialize(run2.output) : void 0,
|
|
630
|
+
success: true
|
|
631
|
+
});
|
|
632
|
+
return;
|
|
633
|
+
case "error":
|
|
634
|
+
resolve({
|
|
635
|
+
error: run2.error ? deserializeError(run2.error) : new UnknownError(),
|
|
636
|
+
success: false
|
|
637
|
+
});
|
|
638
|
+
return;
|
|
639
|
+
case "cancelled":
|
|
640
|
+
resolve({
|
|
641
|
+
error: new RunCancelledError(),
|
|
642
|
+
success: false
|
|
643
|
+
});
|
|
644
|
+
return;
|
|
645
|
+
case "max_recovery_attempts_exceeded":
|
|
646
|
+
resolve({
|
|
647
|
+
error: run2.error ? deserializeError(run2.error) : new MaxRecoveryAttemptsExceededError2(),
|
|
648
|
+
success: false
|
|
649
|
+
});
|
|
650
|
+
return;
|
|
608
651
|
}
|
|
609
|
-
resolve({
|
|
610
|
-
data: completedRun.output ? deserialize(completedRun.output) : void 0,
|
|
611
|
-
success: true
|
|
612
|
-
});
|
|
613
652
|
} catch (error) {
|
|
653
|
+
if (error instanceof RunNotFoundError) {
|
|
654
|
+
reject(error);
|
|
655
|
+
return;
|
|
656
|
+
}
|
|
614
657
|
resolve({
|
|
615
658
|
error,
|
|
616
659
|
success: false
|
|
@@ -647,7 +690,70 @@ async function insertPendingRun(db, options) {
|
|
|
647
690
|
changeId: result.change_id
|
|
648
691
|
};
|
|
649
692
|
}
|
|
693
|
+
async function enqueueRun(db, options) {
|
|
694
|
+
const result = await db.insertInto("runs").values({
|
|
695
|
+
id: options.runId,
|
|
696
|
+
path: options.path,
|
|
697
|
+
inputs: options.inputs,
|
|
698
|
+
queue_name: options.queueName,
|
|
699
|
+
queue_partition_key: options.queuePartitionKey,
|
|
700
|
+
queue_deduplication_id: options.deduplicationId,
|
|
701
|
+
executor_id: options.executorId,
|
|
702
|
+
workflow_name: options.workflowName,
|
|
703
|
+
status: "queued",
|
|
704
|
+
recovery_attempts: options.recoveryAttempts,
|
|
705
|
+
created_at: sql`(extract(epoch from now()) * 1000)::bigint`,
|
|
706
|
+
updated_at: sql`(extract(epoch from now()) * 1000)::bigint`
|
|
707
|
+
}).onConflict((oc) => oc.columns(["queue_name", "queue_deduplication_id"]).doNothing()).returning(["id", "change_id"]).executeTakeFirst();
|
|
708
|
+
return {
|
|
709
|
+
runId: result?.id,
|
|
710
|
+
changeId: result?.change_id
|
|
711
|
+
};
|
|
712
|
+
}
|
|
713
|
+
|
|
714
|
+
// core/internal/repository/insert-message.ts
|
|
715
|
+
async function insertMessage(db, options) {
|
|
716
|
+
return await db.insertInto("messages").values({
|
|
717
|
+
destination_run_id: options.destinationWorkflowId,
|
|
718
|
+
type: options.messageType,
|
|
719
|
+
payload: options.data
|
|
720
|
+
}).execute();
|
|
721
|
+
}
|
|
722
|
+
|
|
723
|
+
// core/internal/get-state.ts
|
|
724
|
+
var StateNotAvailableError = class extends Error {
|
|
725
|
+
};
|
|
726
|
+
async function getState2(ctx, target, key) {
|
|
727
|
+
const { db, stateEventBus } = ctx;
|
|
728
|
+
const destinationWorkflowId = typeof target === "string" ? target : target.id;
|
|
729
|
+
const stateKey = typeof key === "string" ? key : key.name;
|
|
730
|
+
while (true) {
|
|
731
|
+
try {
|
|
732
|
+
return await withDbRetry(async () => {
|
|
733
|
+
const state = await getState(db, destinationWorkflowId, stateKey);
|
|
734
|
+
if (!state) {
|
|
735
|
+
throw new StateNotAvailableError();
|
|
736
|
+
}
|
|
737
|
+
return deserialize(state);
|
|
738
|
+
});
|
|
739
|
+
} catch (error) {
|
|
740
|
+
if (error instanceof StateNotAvailableError) {
|
|
741
|
+
await waitForStateNotification(stateEventBus, destinationWorkflowId, stateKey);
|
|
742
|
+
continue;
|
|
743
|
+
}
|
|
744
|
+
throw error;
|
|
745
|
+
}
|
|
746
|
+
}
|
|
747
|
+
}
|
|
748
|
+
async function waitForStateNotification(stateEventBus, runId, key) {
|
|
749
|
+
return new Promise((resolve) => {
|
|
750
|
+
const unsubscribe = stateEventBus.subscribe(runId, key, (state) => {
|
|
751
|
+
unsubscribe();
|
|
752
|
+
resolve(state);
|
|
753
|
+
});
|
|
754
|
+
});
|
|
755
|
+
}
|
|
650
756
|
|
|
651
|
-
export { ErrorThatShouldNeverHappen, FatalError, MaxRecoveryAttemptsExceededError, MaxRetriesExceededError, QueueNotFoundError, RunCancelledError, RunNotFoundError,
|
|
652
|
-
//# sourceMappingURL=chunk-
|
|
653
|
-
//# sourceMappingURL=chunk-
|
|
757
|
+
export { ErrorThatShouldNeverHappen, FatalError, MaxRecoveryAttemptsExceededError, MaxRetriesExceededError, OperationTimedOutError, QueueNotFoundError, RunCancelledError, RunNotFoundError, StateNotAvailableError, TERMINAL_STATES, TimeoutError, WorkflowNotFoundError, createRunHandle, defineWorkflow, deserialize, deserializeError, enqueueRun, executeAndRecordOperation, executeWorkflow, getExecutionContext, getRun, getRunStatus2 as getRunStatus, getState, getState2, insertMessage, insertPendingRun, returnOrThrowOperationResult, serialize, serializeError, sleep, waitForRunResult, waitForStateNotification, withDbRetry };
|
|
758
|
+
//# sourceMappingURL=chunk-TZSPUZQ3.js.map
|
|
759
|
+
//# sourceMappingURL=chunk-TZSPUZQ3.js.map
|