pg-workflows 0.10.0 → 0.12.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/README.md +43 -0
- package/dist/client.entry.cjs +3 -11
- package/dist/client.entry.d.cts +26 -6
- package/dist/client.entry.d.ts +26 -6
- package/dist/client.entry.js +6 -2
- package/dist/client.entry.js.map +4 -4
- package/dist/index.cjs +221 -49
- package/dist/index.d.cts +27 -22
- package/dist/index.d.ts +27 -22
- package/dist/index.js +226 -41
- package/dist/index.js.map +8 -7
- package/dist/shared/{chunk-nygamc7b.js → chunk-ahxqsytt.js} +3 -13
- package/dist/shared/chunk-ahxqsytt.js.map +16 -0
- package/package.json +10 -1
- package/dist/shared/chunk-nygamc7b.js.map +0 -16
package/dist/index.cjs
CHANGED
|
@@ -65,16 +65,13 @@ var __export = (target, all) => {
|
|
|
65
65
|
var exports_src = {};
|
|
66
66
|
__export(exports_src, {
|
|
67
67
|
workflow: () => workflow,
|
|
68
|
-
|
|
69
|
-
validateResourceId: () => validateResourceId,
|
|
70
|
-
parseDuration: () => parseDuration,
|
|
68
|
+
otelPlugin: () => otelPlugin,
|
|
71
69
|
createWorkflowRef: () => createWorkflowRef,
|
|
72
70
|
WorkflowStatus: () => WorkflowStatus,
|
|
73
71
|
WorkflowRunNotFoundError: () => WorkflowRunNotFoundError,
|
|
74
72
|
WorkflowEngineError: () => WorkflowEngineError,
|
|
75
73
|
WorkflowEngine: () => WorkflowEngine,
|
|
76
|
-
WorkflowClient: () => WorkflowClient
|
|
77
|
-
StepType: () => StepType
|
|
74
|
+
WorkflowClient: () => WorkflowClient
|
|
78
75
|
});
|
|
79
76
|
module.exports = __toCommonJS(exports_src);
|
|
80
77
|
|
|
@@ -543,16 +540,6 @@ var WorkflowStatus;
|
|
|
543
540
|
WorkflowStatus2["FAILED"] = "failed";
|
|
544
541
|
WorkflowStatus2["CANCELLED"] = "cancelled";
|
|
545
542
|
})(WorkflowStatus ||= {});
|
|
546
|
-
var StepType;
|
|
547
|
-
((StepType2) => {
|
|
548
|
-
StepType2["PAUSE"] = "pause";
|
|
549
|
-
StepType2["RUN"] = "run";
|
|
550
|
-
StepType2["WAIT_FOR"] = "waitFor";
|
|
551
|
-
StepType2["WAIT_UNTIL"] = "waitUntil";
|
|
552
|
-
StepType2["DELAY"] = "delay";
|
|
553
|
-
StepType2["POLL"] = "poll";
|
|
554
|
-
StepType2["INVOKE_CHILD_WORKFLOW"] = "invokeChildWorkflow";
|
|
555
|
-
})(StepType ||= {});
|
|
556
543
|
|
|
557
544
|
// src/client.ts
|
|
558
545
|
var LOG_PREFIX = "[WorkflowClient]";
|
|
@@ -892,31 +879,6 @@ function createWorkflowFactory(plugins = []) {
|
|
|
892
879
|
return factory;
|
|
893
880
|
}
|
|
894
881
|
var workflow = createWorkflowFactory();
|
|
895
|
-
// src/duration.ts
|
|
896
|
-
var import_parse_duration = __toESM(require("parse-duration"));
|
|
897
|
-
var MS_PER_SECOND = 1000;
|
|
898
|
-
var MS_PER_MINUTE = 60 * MS_PER_SECOND;
|
|
899
|
-
var MS_PER_HOUR = 60 * MS_PER_MINUTE;
|
|
900
|
-
var MS_PER_DAY = 24 * MS_PER_HOUR;
|
|
901
|
-
var MS_PER_WEEK = 7 * MS_PER_DAY;
|
|
902
|
-
function parseDuration(duration) {
|
|
903
|
-
if (typeof duration === "string") {
|
|
904
|
-
if (duration.trim() === "") {
|
|
905
|
-
throw new WorkflowEngineError("Invalid duration: empty string");
|
|
906
|
-
}
|
|
907
|
-
const ms2 = import_parse_duration.default(duration);
|
|
908
|
-
if (ms2 == null || ms2 <= 0) {
|
|
909
|
-
throw new WorkflowEngineError(`Invalid duration: "${duration}"`);
|
|
910
|
-
}
|
|
911
|
-
return ms2;
|
|
912
|
-
}
|
|
913
|
-
const { weeks = 0, days = 0, hours = 0, minutes = 0, seconds = 0 } = duration;
|
|
914
|
-
const ms = weeks * MS_PER_WEEK + days * MS_PER_DAY + hours * MS_PER_HOUR + minutes * MS_PER_MINUTE + seconds * MS_PER_SECOND;
|
|
915
|
-
if (ms <= 0) {
|
|
916
|
-
throw new WorkflowEngineError("Invalid duration: must be a positive value");
|
|
917
|
-
}
|
|
918
|
-
return ms;
|
|
919
|
-
}
|
|
920
882
|
// src/engine.ts
|
|
921
883
|
var import_es_toolkit2 = require("es-toolkit");
|
|
922
884
|
var import_pg2 = __toESM(require("pg"));
|
|
@@ -992,6 +954,32 @@ function parseWorkflowHandler(handler) {
|
|
|
992
954
|
return { steps: Array.from(steps.values()) };
|
|
993
955
|
}
|
|
994
956
|
|
|
957
|
+
// src/duration.ts
|
|
958
|
+
var import_parse_duration = __toESM(require("parse-duration"));
|
|
959
|
+
var MS_PER_SECOND = 1000;
|
|
960
|
+
var MS_PER_MINUTE = 60 * MS_PER_SECOND;
|
|
961
|
+
var MS_PER_HOUR = 60 * MS_PER_MINUTE;
|
|
962
|
+
var MS_PER_DAY = 24 * MS_PER_HOUR;
|
|
963
|
+
var MS_PER_WEEK = 7 * MS_PER_DAY;
|
|
964
|
+
function parseDuration(duration) {
|
|
965
|
+
if (typeof duration === "string") {
|
|
966
|
+
if (duration.trim() === "") {
|
|
967
|
+
throw new WorkflowEngineError("Invalid duration: empty string");
|
|
968
|
+
}
|
|
969
|
+
const ms2 = import_parse_duration.default(duration);
|
|
970
|
+
if (ms2 == null || ms2 <= 0) {
|
|
971
|
+
throw new WorkflowEngineError(`Invalid duration: "${duration}"`);
|
|
972
|
+
}
|
|
973
|
+
return ms2;
|
|
974
|
+
}
|
|
975
|
+
const { weeks = 0, days = 0, hours = 0, minutes = 0, seconds = 0 } = duration;
|
|
976
|
+
const ms = weeks * MS_PER_WEEK + days * MS_PER_DAY + hours * MS_PER_HOUR + minutes * MS_PER_MINUTE + seconds * MS_PER_SECOND;
|
|
977
|
+
if (ms <= 0) {
|
|
978
|
+
throw new WorkflowEngineError("Invalid duration: must be a positive value");
|
|
979
|
+
}
|
|
980
|
+
return ms;
|
|
981
|
+
}
|
|
982
|
+
|
|
995
983
|
// src/engine.ts
|
|
996
984
|
var LOG_PREFIX2 = "[WorkflowEngine]";
|
|
997
985
|
var StepTypeToIcon = {
|
|
@@ -1141,7 +1129,7 @@ class WorkflowEngine {
|
|
|
1141
1129
|
async startWorkflow(refOrParams, inputArg, optionsArg) {
|
|
1142
1130
|
const { workflowId, input, resourceId, idempotencyKey, options } = this.resolveWorkflowRunParameters(refOrParams, inputArg, optionsArg);
|
|
1143
1131
|
if (!this._started) {
|
|
1144
|
-
await this.start(false
|
|
1132
|
+
await this.start(false);
|
|
1145
1133
|
}
|
|
1146
1134
|
const { run } = await this.createWorkflowRun({
|
|
1147
1135
|
workflowId,
|
|
@@ -1602,19 +1590,32 @@ class WorkflowEngine {
|
|
|
1602
1590
|
};
|
|
1603
1591
|
let step = { ...baseStep };
|
|
1604
1592
|
const plugins = workflow2.plugins ?? [];
|
|
1605
|
-
for (const plugin of plugins) {
|
|
1606
|
-
const extra = plugin.methods(step);
|
|
1607
|
-
step = { ...step, ...extra };
|
|
1608
|
-
}
|
|
1609
1593
|
const context = {
|
|
1610
1594
|
input: run.input,
|
|
1611
1595
|
workflowId: run.workflowId,
|
|
1612
1596
|
runId: run.id,
|
|
1613
|
-
|
|
1597
|
+
resourceId: run.resourceId ?? undefined,
|
|
1598
|
+
attempt: run.retryCount,
|
|
1599
|
+
get timeline() {
|
|
1600
|
+
return run?.timeline ?? {};
|
|
1601
|
+
},
|
|
1614
1602
|
logger: this.logger,
|
|
1615
1603
|
step
|
|
1616
1604
|
};
|
|
1617
|
-
const
|
|
1605
|
+
for (const plugin of plugins) {
|
|
1606
|
+
const extra = plugin.methods(step, context);
|
|
1607
|
+
step = { ...step, ...extra };
|
|
1608
|
+
context.step = step;
|
|
1609
|
+
}
|
|
1610
|
+
let next = () => workflow2.handler(context);
|
|
1611
|
+
for (const plugin of [...plugins].reverse()) {
|
|
1612
|
+
if (plugin.wrap) {
|
|
1613
|
+
const inner = next;
|
|
1614
|
+
const wrap = plugin.wrap;
|
|
1615
|
+
next = () => wrap(context, inner);
|
|
1616
|
+
}
|
|
1617
|
+
}
|
|
1618
|
+
const result = await next();
|
|
1618
1619
|
run = await this.getRun({ runId, resourceId: scopedResourceId });
|
|
1619
1620
|
const isLastParsedStep = run.currentStepId === workflow2.steps[workflow2.steps.length - 1]?.id;
|
|
1620
1621
|
const hasPluginSteps = (workflow2.plugins?.length ?? 0) > 0;
|
|
@@ -1907,7 +1908,7 @@ class WorkflowEngine {
|
|
|
1907
1908
|
if (output === undefined) {
|
|
1908
1909
|
output = {};
|
|
1909
1910
|
}
|
|
1910
|
-
|
|
1911
|
+
const updated = await this.updateRun({
|
|
1911
1912
|
runId: run.id,
|
|
1912
1913
|
resourceId: run.resourceId ?? undefined,
|
|
1913
1914
|
data: {
|
|
@@ -1919,6 +1920,7 @@ class WorkflowEngine {
|
|
|
1919
1920
|
})
|
|
1920
1921
|
}
|
|
1921
1922
|
}, { db });
|
|
1923
|
+
Object.assign(run, updated);
|
|
1922
1924
|
return output;
|
|
1923
1925
|
} catch (error) {
|
|
1924
1926
|
this.logger.error(`Step ${stepId} failed:`, error, {
|
|
@@ -2146,6 +2148,176 @@ ${error.stack}` : String(error)
|
|
|
2146
2148
|
}, this.db);
|
|
2147
2149
|
}
|
|
2148
2150
|
}
|
|
2151
|
+
// src/plugins/otel.ts
|
|
2152
|
+
var import_api = require("@opentelemetry/api");
|
|
2153
|
+
var DEFAULT_PREFIX = "pg_workflows";
|
|
2154
|
+
function isCachedHit(timeline, stepId, kind) {
|
|
2155
|
+
const entry = timeline[stepId];
|
|
2156
|
+
if (entry && typeof entry === "object" && "output" in entry && entry.output !== undefined) {
|
|
2157
|
+
return true;
|
|
2158
|
+
}
|
|
2159
|
+
if (kind === "invokeChildWorkflow" && timeline[invokeChildWorkflowTimelineKey(stepId)]) {
|
|
2160
|
+
return true;
|
|
2161
|
+
}
|
|
2162
|
+
return false;
|
|
2163
|
+
}
|
|
2164
|
+
function otelPlugin(options = {}) {
|
|
2165
|
+
const tracer = options.tracer ?? import_api.trace.getTracer("pg-workflows");
|
|
2166
|
+
const prefix = options.spanNamePrefix ?? DEFAULT_PREFIX;
|
|
2167
|
+
const extraAttrs = options.attributes;
|
|
2168
|
+
return {
|
|
2169
|
+
name: "opentelemetry",
|
|
2170
|
+
methods: (step, context) => {
|
|
2171
|
+
const wrapVoidish = (kind, base) => {
|
|
2172
|
+
return async (stepId, ...args) => {
|
|
2173
|
+
if (isCachedHit(context.timeline, stepId, kind)) {
|
|
2174
|
+
return base(stepId, ...args);
|
|
2175
|
+
}
|
|
2176
|
+
const capturedCtx = import_api.context.active();
|
|
2177
|
+
const startTime = new Date;
|
|
2178
|
+
let result;
|
|
2179
|
+
let originalErr;
|
|
2180
|
+
let thrownError;
|
|
2181
|
+
try {
|
|
2182
|
+
result = await base(stepId, ...args);
|
|
2183
|
+
} catch (err) {
|
|
2184
|
+
originalErr = err;
|
|
2185
|
+
thrownError = err instanceof Error ? err : new Error(String(err));
|
|
2186
|
+
}
|
|
2187
|
+
const span = tracer.startSpan(`${prefix}.step.${kind}`, {
|
|
2188
|
+
startTime,
|
|
2189
|
+
attributes: { "step.id": stepId, "step.type": kind }
|
|
2190
|
+
}, capturedCtx);
|
|
2191
|
+
if (thrownError) {
|
|
2192
|
+
span.recordException(thrownError);
|
|
2193
|
+
span.setStatus({ code: import_api.SpanStatusCode.ERROR, message: thrownError.message });
|
|
2194
|
+
span.end();
|
|
2195
|
+
throw originalErr;
|
|
2196
|
+
}
|
|
2197
|
+
span.setStatus({ code: import_api.SpanStatusCode.OK });
|
|
2198
|
+
span.end();
|
|
2199
|
+
return result;
|
|
2200
|
+
};
|
|
2201
|
+
};
|
|
2202
|
+
return {
|
|
2203
|
+
run: async (stepId, handler) => {
|
|
2204
|
+
if (isCachedHit(context.timeline, stepId, "run")) {
|
|
2205
|
+
return step.run(stepId, handler);
|
|
2206
|
+
}
|
|
2207
|
+
const capturedCtx = import_api.context.active();
|
|
2208
|
+
const startTime = new Date;
|
|
2209
|
+
let result;
|
|
2210
|
+
let originalErr;
|
|
2211
|
+
let thrownError;
|
|
2212
|
+
try {
|
|
2213
|
+
result = await step.run(stepId, handler);
|
|
2214
|
+
} catch (err) {
|
|
2215
|
+
originalErr = err;
|
|
2216
|
+
thrownError = err instanceof Error ? err : new Error(String(err));
|
|
2217
|
+
}
|
|
2218
|
+
if (result === undefined && !thrownError) {
|
|
2219
|
+
return;
|
|
2220
|
+
}
|
|
2221
|
+
const span = tracer.startSpan(`${prefix}.step.run`, {
|
|
2222
|
+
startTime,
|
|
2223
|
+
attributes: { "step.id": stepId, "step.type": "run" }
|
|
2224
|
+
}, capturedCtx);
|
|
2225
|
+
if (thrownError) {
|
|
2226
|
+
span.recordException(thrownError);
|
|
2227
|
+
span.setStatus({ code: import_api.SpanStatusCode.ERROR, message: thrownError.message });
|
|
2228
|
+
span.end();
|
|
2229
|
+
throw originalErr;
|
|
2230
|
+
}
|
|
2231
|
+
span.setStatus({ code: import_api.SpanStatusCode.OK });
|
|
2232
|
+
span.end();
|
|
2233
|
+
return result;
|
|
2234
|
+
},
|
|
2235
|
+
waitFor: wrapVoidish("waitFor", step.waitFor),
|
|
2236
|
+
delay: wrapVoidish("delay", step.delay),
|
|
2237
|
+
sleep: wrapVoidish("delay", step.delay),
|
|
2238
|
+
waitUntil: wrapVoidish("waitUntil", step.waitUntil),
|
|
2239
|
+
pause: wrapVoidish("pause", step.pause),
|
|
2240
|
+
poll: async (stepId, conditionFn, pollOptions) => {
|
|
2241
|
+
const capturedCtx = import_api.context.active();
|
|
2242
|
+
const startTime = new Date;
|
|
2243
|
+
let result;
|
|
2244
|
+
let originalErr;
|
|
2245
|
+
let thrownError;
|
|
2246
|
+
try {
|
|
2247
|
+
result = await step.poll(stepId, conditionFn, pollOptions);
|
|
2248
|
+
} catch (err) {
|
|
2249
|
+
originalErr = err;
|
|
2250
|
+
thrownError = err instanceof Error ? err : new Error(String(err));
|
|
2251
|
+
}
|
|
2252
|
+
const span = tracer.startSpan(`${prefix}.step.poll`, {
|
|
2253
|
+
startTime,
|
|
2254
|
+
attributes: { "step.id": stepId, "step.type": "poll" }
|
|
2255
|
+
}, capturedCtx);
|
|
2256
|
+
if (thrownError) {
|
|
2257
|
+
span.recordException(thrownError);
|
|
2258
|
+
span.setStatus({ code: import_api.SpanStatusCode.ERROR, message: thrownError.message });
|
|
2259
|
+
span.end();
|
|
2260
|
+
throw originalErr;
|
|
2261
|
+
}
|
|
2262
|
+
span.setStatus({ code: import_api.SpanStatusCode.OK });
|
|
2263
|
+
span.end();
|
|
2264
|
+
return result;
|
|
2265
|
+
},
|
|
2266
|
+
invokeChildWorkflow: async (stepId, refOrParams, inputArg, optionsArg) => {
|
|
2267
|
+
if (isCachedHit(context.timeline, stepId, "invokeChildWorkflow")) {
|
|
2268
|
+
return step.invokeChildWorkflow(stepId, refOrParams, inputArg, optionsArg);
|
|
2269
|
+
}
|
|
2270
|
+
const capturedCtx = import_api.context.active();
|
|
2271
|
+
const startTime = new Date;
|
|
2272
|
+
let result;
|
|
2273
|
+
let originalErr;
|
|
2274
|
+
let thrownError;
|
|
2275
|
+
try {
|
|
2276
|
+
result = await step.invokeChildWorkflow(stepId, refOrParams, inputArg, optionsArg);
|
|
2277
|
+
} catch (err) {
|
|
2278
|
+
originalErr = err;
|
|
2279
|
+
thrownError = err instanceof Error ? err : new Error(String(err));
|
|
2280
|
+
}
|
|
2281
|
+
const span = tracer.startSpan(`${prefix}.step.invokeChildWorkflow`, {
|
|
2282
|
+
startTime,
|
|
2283
|
+
attributes: { "step.id": stepId, "step.type": "invokeChildWorkflow" }
|
|
2284
|
+
}, capturedCtx);
|
|
2285
|
+
if (thrownError) {
|
|
2286
|
+
span.recordException(thrownError);
|
|
2287
|
+
span.setStatus({ code: import_api.SpanStatusCode.ERROR, message: thrownError.message });
|
|
2288
|
+
span.end();
|
|
2289
|
+
throw originalErr;
|
|
2290
|
+
}
|
|
2291
|
+
span.setStatus({ code: import_api.SpanStatusCode.OK });
|
|
2292
|
+
span.end();
|
|
2293
|
+
return result;
|
|
2294
|
+
}
|
|
2295
|
+
};
|
|
2296
|
+
},
|
|
2297
|
+
wrap: (context, next) => tracer.startActiveSpan(`${prefix}.workflow.run`, {
|
|
2298
|
+
attributes: {
|
|
2299
|
+
"workflow.id": context.workflowId,
|
|
2300
|
+
"workflow.run_id": context.runId,
|
|
2301
|
+
"workflow.attempt": context.attempt,
|
|
2302
|
+
...context.resourceId ? { "workflow.resource_id": context.resourceId } : {},
|
|
2303
|
+
...extraAttrs ? extraAttrs(context) : {}
|
|
2304
|
+
}
|
|
2305
|
+
}, async (span) => {
|
|
2306
|
+
try {
|
|
2307
|
+
const result = await next();
|
|
2308
|
+
span.setStatus({ code: import_api.SpanStatusCode.OK });
|
|
2309
|
+
return result;
|
|
2310
|
+
} catch (err) {
|
|
2311
|
+
const error = err instanceof Error ? err : new Error(String(err));
|
|
2312
|
+
span.recordException(error);
|
|
2313
|
+
span.setStatus({ code: import_api.SpanStatusCode.ERROR, message: error.message });
|
|
2314
|
+
throw err;
|
|
2315
|
+
} finally {
|
|
2316
|
+
span.end();
|
|
2317
|
+
}
|
|
2318
|
+
})
|
|
2319
|
+
};
|
|
2320
|
+
}
|
|
2149
2321
|
|
|
2150
|
-
//# debugId=
|
|
2322
|
+
//# debugId=BCF84547491115D464756E2164756E21
|
|
2151
2323
|
//# sourceMappingURL=index.js.map
|
package/dist/index.d.cts
CHANGED
|
@@ -33,7 +33,6 @@ type DurationObject = {
|
|
|
33
33
|
seconds?: number;
|
|
34
34
|
};
|
|
35
35
|
type Duration = string | DurationObject;
|
|
36
|
-
declare function parseDuration(duration: Duration): number;
|
|
37
36
|
declare enum WorkflowStatus {
|
|
38
37
|
PENDING = "pending",
|
|
39
38
|
RUNNING = "running",
|
|
@@ -53,7 +52,7 @@ declare enum StepType {
|
|
|
53
52
|
}
|
|
54
53
|
type InputParameters = StandardSchemaV1;
|
|
55
54
|
type InferInputParameters<P extends InputParameters> = StandardSchemaV1.InferOutput<P>;
|
|
56
|
-
type
|
|
55
|
+
type StartWorkflowOptions = {
|
|
57
56
|
resourceId?: string;
|
|
58
57
|
timeout?: number;
|
|
59
58
|
retries?: number;
|
|
@@ -107,13 +106,13 @@ type StepBaseContext = {
|
|
|
107
106
|
<
|
|
108
107
|
TInput extends InputParameters,
|
|
109
108
|
TOutput = unknown
|
|
110
|
-
>(stepId: string, ref: WorkflowRef<TInput, TOutput>, input: InferInputParameters<TInput>, options?:
|
|
109
|
+
>(stepId: string, ref: WorkflowRef<TInput, TOutput>, input: InferInputParameters<TInput>, options?: StartWorkflowOptions): Promise<TOutput>;
|
|
111
110
|
<TOutput = unknown>(stepId: string, params: {
|
|
112
111
|
workflowId: string;
|
|
113
112
|
input: unknown;
|
|
114
113
|
resourceId?: string;
|
|
115
114
|
idempotencyKey?: string;
|
|
116
|
-
options?:
|
|
115
|
+
options?: StartWorkflowOptions;
|
|
117
116
|
}): Promise<TOutput>;
|
|
118
117
|
};
|
|
119
118
|
};
|
|
@@ -127,7 +126,13 @@ interface WorkflowPlugin<
|
|
|
127
126
|
TStepExt = object
|
|
128
127
|
> {
|
|
129
128
|
name: string;
|
|
130
|
-
methods: (step: TStepBase) => TStepExt;
|
|
129
|
+
methods: (step: TStepBase, context: WorkflowContext) => TStepExt;
|
|
130
|
+
/**
|
|
131
|
+
* Optional middleware around the workflow handler call. Composes in
|
|
132
|
+
* registration order — the first plugin passed to `.use()` wraps everything
|
|
133
|
+
* inside. Implementations MUST call `next()` exactly once.
|
|
134
|
+
*/
|
|
135
|
+
wrap?: (context: WorkflowContext, next: () => Promise<unknown>) => Promise<unknown>;
|
|
131
136
|
}
|
|
132
137
|
type WorkflowContext<
|
|
133
138
|
TInput extends InputParameters = InputParameters,
|
|
@@ -137,6 +142,10 @@ type WorkflowContext<
|
|
|
137
142
|
step: TStep;
|
|
138
143
|
workflowId: string;
|
|
139
144
|
runId: string;
|
|
145
|
+
/** Tenant/scope identifier set when the run was started, if any. */
|
|
146
|
+
resourceId?: string;
|
|
147
|
+
/** Zero-based retry attempt number (= `run.retryCount`). */
|
|
148
|
+
attempt: number;
|
|
140
149
|
timeline: Record<string, unknown>;
|
|
141
150
|
logger: WorkflowLogger;
|
|
142
151
|
};
|
|
@@ -197,14 +206,6 @@ interface WorkflowLogger {
|
|
|
197
206
|
log(message: string): void;
|
|
198
207
|
error(message: string, ...args: unknown[]): void;
|
|
199
208
|
}
|
|
200
|
-
type WorkflowInternalLoggerContext = {
|
|
201
|
-
runId?: string;
|
|
202
|
-
workflowId?: string;
|
|
203
|
-
};
|
|
204
|
-
interface WorkflowInternalLogger {
|
|
205
|
-
log(message: string, context?: WorkflowInternalLoggerContext): void;
|
|
206
|
-
error(message: string, error: Error, context?: WorkflowInternalLoggerContext): void;
|
|
207
|
-
}
|
|
208
209
|
type WorkflowClientOptions = {
|
|
209
210
|
logger?: WorkflowLogger;
|
|
210
211
|
/**
|
|
@@ -221,7 +222,6 @@ type WorkflowClientOptions = {
|
|
|
221
222
|
connectionString: string;
|
|
222
223
|
pool?: never;
|
|
223
224
|
});
|
|
224
|
-
type StartWorkflowOptions = WorkflowRunOptions;
|
|
225
225
|
declare class WorkflowClient {
|
|
226
226
|
private boss;
|
|
227
227
|
private db;
|
|
@@ -306,9 +306,6 @@ declare function createWorkflowRef<
|
|
|
306
306
|
declare const workflow: WorkflowFactory;
|
|
307
307
|
import pg2 from "pg";
|
|
308
308
|
import { Db, PgBoss as PgBoss2 } from "pg-boss";
|
|
309
|
-
type StartWorkflowOptions2 = WorkflowRunOptions & {
|
|
310
|
-
batchSize?: number;
|
|
311
|
-
};
|
|
312
309
|
type WorkflowEngineOptions = {
|
|
313
310
|
workflows?: WorkflowDefinition[];
|
|
314
311
|
logger?: WorkflowLogger;
|
|
@@ -339,13 +336,13 @@ declare class WorkflowEngine {
|
|
|
339
336
|
unregisterWorkflow(workflowId: string): Promise<WorkflowEngine>;
|
|
340
337
|
unregisterAllWorkflows(): Promise<WorkflowEngine>;
|
|
341
338
|
private resolveWorkflowRunParameters;
|
|
342
|
-
startWorkflow<TInput extends InputParameters>(ref: WorkflowRef<TInput>, input: InferInputParameters<TInput>, options?:
|
|
339
|
+
startWorkflow<TInput extends InputParameters>(ref: WorkflowRef<TInput>, input: InferInputParameters<TInput>, options?: StartWorkflowOptions): Promise<WorkflowRun>;
|
|
343
340
|
startWorkflow(params: {
|
|
344
341
|
resourceId?: string;
|
|
345
342
|
workflowId: string;
|
|
346
343
|
input: unknown;
|
|
347
344
|
idempotencyKey?: string;
|
|
348
|
-
options?:
|
|
345
|
+
options?: StartWorkflowOptions;
|
|
349
346
|
}): Promise<WorkflowRun>;
|
|
350
347
|
private createWorkflowRun;
|
|
351
348
|
private enqueueWorkflowRun;
|
|
@@ -455,8 +452,6 @@ declare class WorkflowEngine {
|
|
|
455
452
|
}>;
|
|
456
453
|
}
|
|
457
454
|
import { StandardSchemaV1 as StandardSchemaV12 } from "@standard-schema/spec";
|
|
458
|
-
declare function validateWorkflowId(workflowId: string): void;
|
|
459
|
-
declare function validateResourceId(resourceId: string | undefined | null): void;
|
|
460
455
|
declare class WorkflowEngineError extends Error {
|
|
461
456
|
readonly workflowId?: string | undefined;
|
|
462
457
|
readonly runId?: string | undefined;
|
|
@@ -467,4 +462,14 @@ declare class WorkflowEngineError extends Error {
|
|
|
467
462
|
declare class WorkflowRunNotFoundError extends WorkflowEngineError {
|
|
468
463
|
constructor(runId?: string, workflowId?: string);
|
|
469
464
|
}
|
|
470
|
-
|
|
465
|
+
import { AttributeValue, Tracer } from "@opentelemetry/api";
|
|
466
|
+
type OtelPluginOptions = {
|
|
467
|
+
/** Tracer to use. Defaults to `trace.getTracer('pg-workflows')`. */
|
|
468
|
+
tracer?: Tracer;
|
|
469
|
+
/** Prefix for all span names. Defaults to `pg_workflows`. */
|
|
470
|
+
spanNamePrefix?: string;
|
|
471
|
+
/** Extra attributes merged onto the workflow.run span. */
|
|
472
|
+
attributes?: (context: WorkflowContext) => Record<string, AttributeValue>;
|
|
473
|
+
};
|
|
474
|
+
declare function otelPlugin(options?: OtelPluginOptions): WorkflowPlugin<StepBaseContext, object>;
|
|
475
|
+
export { workflow, otelPlugin, createWorkflowRef, WorkflowStatus, WorkflowRunProgress, WorkflowRunNotFoundError, WorkflowRun, WorkflowRef, WorkflowPlugin, WorkflowOptions, WorkflowLogger, WorkflowEngineOptions, WorkflowEngineError, WorkflowEngine, WorkflowDefinition, WorkflowContext, WorkflowClientOptions, WorkflowClient, StepBaseContext, StartWorkflowOptions, OtelPluginOptions, InputParameters, InferInputParameters, Duration };
|
package/dist/index.d.ts
CHANGED
|
@@ -33,7 +33,6 @@ type DurationObject = {
|
|
|
33
33
|
seconds?: number;
|
|
34
34
|
};
|
|
35
35
|
type Duration = string | DurationObject;
|
|
36
|
-
declare function parseDuration(duration: Duration): number;
|
|
37
36
|
declare enum WorkflowStatus {
|
|
38
37
|
PENDING = "pending",
|
|
39
38
|
RUNNING = "running",
|
|
@@ -53,7 +52,7 @@ declare enum StepType {
|
|
|
53
52
|
}
|
|
54
53
|
type InputParameters = StandardSchemaV1;
|
|
55
54
|
type InferInputParameters<P extends InputParameters> = StandardSchemaV1.InferOutput<P>;
|
|
56
|
-
type
|
|
55
|
+
type StartWorkflowOptions = {
|
|
57
56
|
resourceId?: string;
|
|
58
57
|
timeout?: number;
|
|
59
58
|
retries?: number;
|
|
@@ -107,13 +106,13 @@ type StepBaseContext = {
|
|
|
107
106
|
<
|
|
108
107
|
TInput extends InputParameters,
|
|
109
108
|
TOutput = unknown
|
|
110
|
-
>(stepId: string, ref: WorkflowRef<TInput, TOutput>, input: InferInputParameters<TInput>, options?:
|
|
109
|
+
>(stepId: string, ref: WorkflowRef<TInput, TOutput>, input: InferInputParameters<TInput>, options?: StartWorkflowOptions): Promise<TOutput>;
|
|
111
110
|
<TOutput = unknown>(stepId: string, params: {
|
|
112
111
|
workflowId: string;
|
|
113
112
|
input: unknown;
|
|
114
113
|
resourceId?: string;
|
|
115
114
|
idempotencyKey?: string;
|
|
116
|
-
options?:
|
|
115
|
+
options?: StartWorkflowOptions;
|
|
117
116
|
}): Promise<TOutput>;
|
|
118
117
|
};
|
|
119
118
|
};
|
|
@@ -127,7 +126,13 @@ interface WorkflowPlugin<
|
|
|
127
126
|
TStepExt = object
|
|
128
127
|
> {
|
|
129
128
|
name: string;
|
|
130
|
-
methods: (step: TStepBase) => TStepExt;
|
|
129
|
+
methods: (step: TStepBase, context: WorkflowContext) => TStepExt;
|
|
130
|
+
/**
|
|
131
|
+
* Optional middleware around the workflow handler call. Composes in
|
|
132
|
+
* registration order — the first plugin passed to `.use()` wraps everything
|
|
133
|
+
* inside. Implementations MUST call `next()` exactly once.
|
|
134
|
+
*/
|
|
135
|
+
wrap?: (context: WorkflowContext, next: () => Promise<unknown>) => Promise<unknown>;
|
|
131
136
|
}
|
|
132
137
|
type WorkflowContext<
|
|
133
138
|
TInput extends InputParameters = InputParameters,
|
|
@@ -137,6 +142,10 @@ type WorkflowContext<
|
|
|
137
142
|
step: TStep;
|
|
138
143
|
workflowId: string;
|
|
139
144
|
runId: string;
|
|
145
|
+
/** Tenant/scope identifier set when the run was started, if any. */
|
|
146
|
+
resourceId?: string;
|
|
147
|
+
/** Zero-based retry attempt number (= `run.retryCount`). */
|
|
148
|
+
attempt: number;
|
|
140
149
|
timeline: Record<string, unknown>;
|
|
141
150
|
logger: WorkflowLogger;
|
|
142
151
|
};
|
|
@@ -197,14 +206,6 @@ interface WorkflowLogger {
|
|
|
197
206
|
log(message: string): void;
|
|
198
207
|
error(message: string, ...args: unknown[]): void;
|
|
199
208
|
}
|
|
200
|
-
type WorkflowInternalLoggerContext = {
|
|
201
|
-
runId?: string;
|
|
202
|
-
workflowId?: string;
|
|
203
|
-
};
|
|
204
|
-
interface WorkflowInternalLogger {
|
|
205
|
-
log(message: string, context?: WorkflowInternalLoggerContext): void;
|
|
206
|
-
error(message: string, error: Error, context?: WorkflowInternalLoggerContext): void;
|
|
207
|
-
}
|
|
208
209
|
type WorkflowClientOptions = {
|
|
209
210
|
logger?: WorkflowLogger;
|
|
210
211
|
/**
|
|
@@ -221,7 +222,6 @@ type WorkflowClientOptions = {
|
|
|
221
222
|
connectionString: string;
|
|
222
223
|
pool?: never;
|
|
223
224
|
});
|
|
224
|
-
type StartWorkflowOptions = WorkflowRunOptions;
|
|
225
225
|
declare class WorkflowClient {
|
|
226
226
|
private boss;
|
|
227
227
|
private db;
|
|
@@ -306,9 +306,6 @@ declare function createWorkflowRef<
|
|
|
306
306
|
declare const workflow: WorkflowFactory;
|
|
307
307
|
import pg2 from "pg";
|
|
308
308
|
import { Db, PgBoss as PgBoss2 } from "pg-boss";
|
|
309
|
-
type StartWorkflowOptions2 = WorkflowRunOptions & {
|
|
310
|
-
batchSize?: number;
|
|
311
|
-
};
|
|
312
309
|
type WorkflowEngineOptions = {
|
|
313
310
|
workflows?: WorkflowDefinition[];
|
|
314
311
|
logger?: WorkflowLogger;
|
|
@@ -339,13 +336,13 @@ declare class WorkflowEngine {
|
|
|
339
336
|
unregisterWorkflow(workflowId: string): Promise<WorkflowEngine>;
|
|
340
337
|
unregisterAllWorkflows(): Promise<WorkflowEngine>;
|
|
341
338
|
private resolveWorkflowRunParameters;
|
|
342
|
-
startWorkflow<TInput extends InputParameters>(ref: WorkflowRef<TInput>, input: InferInputParameters<TInput>, options?:
|
|
339
|
+
startWorkflow<TInput extends InputParameters>(ref: WorkflowRef<TInput>, input: InferInputParameters<TInput>, options?: StartWorkflowOptions): Promise<WorkflowRun>;
|
|
343
340
|
startWorkflow(params: {
|
|
344
341
|
resourceId?: string;
|
|
345
342
|
workflowId: string;
|
|
346
343
|
input: unknown;
|
|
347
344
|
idempotencyKey?: string;
|
|
348
|
-
options?:
|
|
345
|
+
options?: StartWorkflowOptions;
|
|
349
346
|
}): Promise<WorkflowRun>;
|
|
350
347
|
private createWorkflowRun;
|
|
351
348
|
private enqueueWorkflowRun;
|
|
@@ -455,8 +452,6 @@ declare class WorkflowEngine {
|
|
|
455
452
|
}>;
|
|
456
453
|
}
|
|
457
454
|
import { StandardSchemaV1 as StandardSchemaV12 } from "@standard-schema/spec";
|
|
458
|
-
declare function validateWorkflowId(workflowId: string): void;
|
|
459
|
-
declare function validateResourceId(resourceId: string | undefined | null): void;
|
|
460
455
|
declare class WorkflowEngineError extends Error {
|
|
461
456
|
readonly workflowId?: string | undefined;
|
|
462
457
|
readonly runId?: string | undefined;
|
|
@@ -467,4 +462,14 @@ declare class WorkflowEngineError extends Error {
|
|
|
467
462
|
declare class WorkflowRunNotFoundError extends WorkflowEngineError {
|
|
468
463
|
constructor(runId?: string, workflowId?: string);
|
|
469
464
|
}
|
|
470
|
-
|
|
465
|
+
import { AttributeValue, Tracer } from "@opentelemetry/api";
|
|
466
|
+
type OtelPluginOptions = {
|
|
467
|
+
/** Tracer to use. Defaults to `trace.getTracer('pg-workflows')`. */
|
|
468
|
+
tracer?: Tracer;
|
|
469
|
+
/** Prefix for all span names. Defaults to `pg_workflows`. */
|
|
470
|
+
spanNamePrefix?: string;
|
|
471
|
+
/** Extra attributes merged onto the workflow.run span. */
|
|
472
|
+
attributes?: (context: WorkflowContext) => Record<string, AttributeValue>;
|
|
473
|
+
};
|
|
474
|
+
declare function otelPlugin(options?: OtelPluginOptions): WorkflowPlugin<StepBaseContext, object>;
|
|
475
|
+
export { workflow, otelPlugin, createWorkflowRef, WorkflowStatus, WorkflowRunProgress, WorkflowRunNotFoundError, WorkflowRun, WorkflowRef, WorkflowPlugin, WorkflowOptions, WorkflowLogger, WorkflowEngineOptions, WorkflowEngineError, WorkflowEngine, WorkflowDefinition, WorkflowContext, WorkflowClientOptions, WorkflowClient, StepBaseContext, StartWorkflowOptions, OtelPluginOptions, InputParameters, InferInputParameters, Duration };
|