@oomol-lab/open-flow 0.1.0-beta.76 → 0.1.0-beta.78
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 +3 -0
- package/dist/browser/{ContentIcon-Cm1hbVzW.js → ContentIcon-CMn0c-kl.js} +99 -6
- package/dist/browser/{FlowCanvas-NzKtla_c.js → FlowCanvas-BQGBcfoL.js} +1709 -613
- package/dist/browser/{createResourceDialog-BgdedQqu.js → createResourceDialog-DCGxfKFM.js} +63 -57
- package/dist/browser/{dialog-aSElFFw2.js → dialog-WzR4CRFH.js} +76 -77
- package/dist/browser/{exportSvg-Dcz4HTo_.js → exportSvg-CYwyYiuH.js} +2 -2
- package/dist/browser/{flowChanges-NZyS7HSp.js → flowChanges-Bz4dbDN_.js} +6875 -11091
- package/dist/browser/{flowWorkspace-Bl0SDehy.js → flowWorkspace-BI6L6a4r.js} +1415 -3037
- package/dist/browser/licenses.md +1 -1
- package/dist/browser/preview.css +619 -462
- package/dist/browser/preview.js +9016 -14956
- package/dist/browser/theme.css +4 -2
- package/dist/browser/{tooltip-3XMK9jkr.js → tooltip-BDcVTNpu.js} +65 -2
- package/dist/browser/{typeScriptSession-C9sBGOKZ.js → typeScriptSession-CRoezJPN.js} +1 -1
- package/dist/browser/ui.css +112 -24
- package/dist/browser/ui.js +3 -2
- package/dist/browser/workbench.css +10020 -9842
- package/dist/browser/workbench.d.ts +5 -2
- package/dist/browser/workbench.js +2382 -2668
- package/dist/browser/{workbenchSelect-DBGP7Y4Z.js → workbenchSelect-DtAd0zc4.js} +2 -2
- package/dist/command/index.js +48 -48
- package/dist/common/authoring.d.ts +4 -4
- package/dist/common/authoringExamples.d.ts +3 -2
- package/dist/common/authoringSchema.d.ts +15 -4
- package/dist/common/control-api-conformance.js +155 -15
- package/dist/common/control-api-errors.d.ts +12 -0
- package/dist/common/control-api.d.ts +39 -2
- package/dist/common/control-api.js +180 -37
- package/dist/common/control-requests.d.ts +23 -3
- package/dist/common/control-requests.js +141 -14
- package/dist/common/engine-contract.d.ts +3 -2
- package/dist/common/flow-authoring.js +47 -7
- package/dist/common/flow-change-schema.d.ts +1 -1
- package/dist/common/flow-change.d.ts +2 -2
- package/dist/common/flow-change.js +48 -8
- package/dist/common/flow-encoding.js +47 -7
- package/dist/common/flow-semantics.js +86 -8
- package/dist/common/flow-state.d.ts +100 -0
- package/dist/common/flow-state.js +5794 -0
- package/dist/common/mcp.d.ts +96 -3
- package/dist/common/mcp.js +158 -13
- package/dist/common/run-events.js +19 -8
- package/dist/common/runtime-contract.d.ts +14 -0
- package/dist/common/runtime-contract.js +124 -17
- package/dist/common/runtime-nodejs-compat.js +11 -12
- package/dist/common/scheduler-node-execution.d.ts +1 -0
- package/dist/common/scheduler.d.ts +2 -1
- package/dist/common/scheduler.js +95 -40
- package/dist/common/state-conformance.d.ts +16 -0
- package/dist/common/tags.d.ts +4 -0
- package/dist/index.d.ts +11 -0
- package/package.json +5 -1
- package/src/control/common/api.ts +101 -11
- package/src/control/common/authoring.ts +7 -1
- package/src/control/common/authoringExamples.ts +9 -0
- package/src/control/common/authoringSchema.ts +18 -12
- package/src/control/common/errors.ts +6 -0
- package/src/control/common/flowDecoders.ts +1 -0
- package/src/control/common/mcp.ts +16 -0
- package/src/control/common/requests.ts +16 -2
- package/src/control/common/tags.ts +20 -0
- package/src/execution/common/events.ts +22 -7
- package/src/execution/common/node-execution.ts +3 -0
- package/src/execution/common/scheduler.ts +29 -13
- package/src/flow/common/change.ts +2 -1
- package/src/flow/common/changeSchema.ts +11 -1
- package/src/flow/common/errorHandling.ts +1 -1
- package/src/flow/common/semantics.ts +27 -1
- package/src/runtime/common/engineContract.ts +6 -3
- package/src/runtime/common/nodejsGuest.generated.json +11 -12
- package/src/runtime/common/runtime.ts +122 -7
- package/src/state/common/conformance.ts +81 -0
- package/src/state/common/state.ts +141 -0
- package/src/types/index.ts +11 -0
package/dist/common/mcp.d.ts
CHANGED
|
@@ -3,6 +3,99 @@ import { z } from 'zod';
|
|
|
3
3
|
export declare const mcpProtocolVersion = "2026-07-28";
|
|
4
4
|
export declare const mcpInstructions: string;
|
|
5
5
|
export declare const mcpTools: {
|
|
6
|
+
flow_state: {
|
|
7
|
+
description: string;
|
|
8
|
+
annotations: {
|
|
9
|
+
readOnlyHint: boolean;
|
|
10
|
+
destructiveHint: boolean;
|
|
11
|
+
idempotentHint: boolean;
|
|
12
|
+
openWorldHint: boolean;
|
|
13
|
+
};
|
|
14
|
+
inputSchema: {
|
|
15
|
+
'~standard': {
|
|
16
|
+
version: 1;
|
|
17
|
+
vendor: string;
|
|
18
|
+
jsonSchema: {
|
|
19
|
+
input: () => Record<string, unknown>;
|
|
20
|
+
output: () => Record<string, unknown>;
|
|
21
|
+
};
|
|
22
|
+
validate(value: unknown): {
|
|
23
|
+
value: {
|
|
24
|
+
scope: "draft" | "live";
|
|
25
|
+
values?: boolean | undefined;
|
|
26
|
+
flowId: string;
|
|
27
|
+
};
|
|
28
|
+
} | {
|
|
29
|
+
issues: {
|
|
30
|
+
message: string;
|
|
31
|
+
path: string[];
|
|
32
|
+
}[];
|
|
33
|
+
};
|
|
34
|
+
};
|
|
35
|
+
};
|
|
36
|
+
};
|
|
37
|
+
flow_state_clear: {
|
|
38
|
+
description: string;
|
|
39
|
+
annotations: {
|
|
40
|
+
readOnlyHint: boolean;
|
|
41
|
+
destructiveHint: boolean;
|
|
42
|
+
idempotentHint: boolean;
|
|
43
|
+
openWorldHint: boolean;
|
|
44
|
+
};
|
|
45
|
+
inputSchema: {
|
|
46
|
+
'~standard': {
|
|
47
|
+
version: 1;
|
|
48
|
+
vendor: string;
|
|
49
|
+
jsonSchema: {
|
|
50
|
+
input: () => Record<string, unknown>;
|
|
51
|
+
output: () => Record<string, unknown>;
|
|
52
|
+
};
|
|
53
|
+
validate(value: unknown): {
|
|
54
|
+
value: {
|
|
55
|
+
scope: "draft" | "live";
|
|
56
|
+
key?: string | undefined;
|
|
57
|
+
flowId: string;
|
|
58
|
+
};
|
|
59
|
+
} | {
|
|
60
|
+
issues: {
|
|
61
|
+
message: string;
|
|
62
|
+
path: string[];
|
|
63
|
+
}[];
|
|
64
|
+
};
|
|
65
|
+
};
|
|
66
|
+
};
|
|
67
|
+
};
|
|
68
|
+
flow_dedupe_clear: {
|
|
69
|
+
description: string;
|
|
70
|
+
annotations: {
|
|
71
|
+
readOnlyHint: boolean;
|
|
72
|
+
destructiveHint: boolean;
|
|
73
|
+
idempotentHint: boolean;
|
|
74
|
+
openWorldHint: boolean;
|
|
75
|
+
};
|
|
76
|
+
inputSchema: {
|
|
77
|
+
'~standard': {
|
|
78
|
+
version: 1;
|
|
79
|
+
vendor: string;
|
|
80
|
+
jsonSchema: {
|
|
81
|
+
input: () => Record<string, unknown>;
|
|
82
|
+
output: () => Record<string, unknown>;
|
|
83
|
+
};
|
|
84
|
+
validate(value: unknown): {
|
|
85
|
+
value: {
|
|
86
|
+
scope: "draft" | "live";
|
|
87
|
+
space: string;
|
|
88
|
+
flowId: string;
|
|
89
|
+
};
|
|
90
|
+
} | {
|
|
91
|
+
issues: {
|
|
92
|
+
message: string;
|
|
93
|
+
path: string[];
|
|
94
|
+
}[];
|
|
95
|
+
};
|
|
96
|
+
};
|
|
97
|
+
};
|
|
98
|
+
};
|
|
6
99
|
flow_canvas: {
|
|
7
100
|
description: string;
|
|
8
101
|
annotations: {
|
|
@@ -161,7 +254,7 @@ export declare const mcpTools: {
|
|
|
161
254
|
value: {
|
|
162
255
|
revision?: string | undefined;
|
|
163
256
|
query: string;
|
|
164
|
-
type?: "agent" | "approval" | "code" | "condition" | "connector" | "cron" | "decision" | "error" | "http-request" | "integration" | "llm" | "openapi" | "outputs" | "poll" | "start" | "value" | "wait" | "webhook" | "webhook-response" | "workflow" | undefined;
|
|
257
|
+
type?: "agent" | "approval" | "code" | "condition" | "connector" | "cron" | "decision" | "error" | "http-request" | "integration" | "llm" | "openapi" | "outputs" | "poll" | "skip-duplicates" | "start" | "value" | "wait" | "webhook" | "webhook-response" | "workflow" | undefined;
|
|
165
258
|
offset: number;
|
|
166
259
|
limit: number;
|
|
167
260
|
flowId: string;
|
|
@@ -193,7 +286,7 @@ export declare const mcpTools: {
|
|
|
193
286
|
};
|
|
194
287
|
validate(value: unknown): {
|
|
195
288
|
value: {
|
|
196
|
-
type?: "agent" | "approval" | "code" | "condition" | "connector" | "cron" | "decision" | "error" | "http-request" | "integration" | "llm" | "openapi" | "outputs" | "poll" | "start" | "value" | "wait" | "webhook" | "webhook-response" | "workflow" | undefined;
|
|
289
|
+
type?: "agent" | "approval" | "code" | "condition" | "connector" | "cron" | "decision" | "error" | "http-request" | "integration" | "llm" | "openapi" | "outputs" | "poll" | "skip-duplicates" | "start" | "value" | "wait" | "webhook" | "webhook-response" | "workflow" | undefined;
|
|
197
290
|
action?: string | undefined;
|
|
198
291
|
flowId?: string | undefined;
|
|
199
292
|
};
|
|
@@ -321,7 +414,7 @@ export declare const mcpTools: {
|
|
|
321
414
|
edits: ({
|
|
322
415
|
op: "node.add";
|
|
323
416
|
as: string;
|
|
324
|
-
type: "agent" | "approval" | "code" | "condition" | "connector" | "cron" | "decision" | "error" | "http-request" | "integration" | "llm" | "openapi" | "outputs" | "poll" | "start" | "value" | "wait" | "webhook" | "webhook-response" | "workflow";
|
|
417
|
+
type: "agent" | "approval" | "code" | "condition" | "connector" | "cron" | "decision" | "error" | "http-request" | "integration" | "llm" | "openapi" | "outputs" | "poll" | "skip-duplicates" | "start" | "value" | "wait" | "webhook" | "webhook-response" | "workflow";
|
|
325
418
|
name: string;
|
|
326
419
|
onError?: "error" | "stop" | undefined;
|
|
327
420
|
retry?: {
|
package/dist/common/mcp.js
CHANGED
|
@@ -8846,6 +8846,46 @@ var httpRequestConfigSchema = strictObject({
|
|
|
8846
8846
|
statusPolicy: _enum(["success", "all"]).default("success")
|
|
8847
8847
|
});
|
|
8848
8848
|
var httpRequestExecutorSchema = httpRequestConfigSchema.extend({ kind: literal("http-request") });
|
|
8849
|
+
//#endregion
|
|
8850
|
+
//#region src/state/common/state.ts
|
|
8851
|
+
var stateQuerySchema = strictObject({
|
|
8852
|
+
scope: _enum(["draft", "live"]),
|
|
8853
|
+
values: boolean().optional()
|
|
8854
|
+
});
|
|
8855
|
+
var stateClearSchema = strictObject({
|
|
8856
|
+
scope: _enum(["draft", "live"]),
|
|
8857
|
+
key: string$1().min(1).refine((key) => new TextEncoder().encode(key).length <= 256).optional()
|
|
8858
|
+
});
|
|
8859
|
+
var dedupeClearSchema = strictObject({
|
|
8860
|
+
scope: _enum(["draft", "live"]),
|
|
8861
|
+
space: string$1().regex(/^(flow|node:.+)$/)
|
|
8862
|
+
});
|
|
8863
|
+
var skipDuplicatesConfigSchema = strictObject({ fields: array(string$1().refine((field) => field.length > 0 && field.split(".").every((part) => part.length > 0), "Use a nonempty dot-separated field path.")).refine((fields) => new Set(fields).size === fields.length, "Identity fields must be distinct.").default([]) });
|
|
8864
|
+
var skipDuplicatesExecutorSchema = skipDuplicatesConfigSchema.extend({ kind: literal("skip-duplicates") });
|
|
8865
|
+
var flowStateViewSchema = object({
|
|
8866
|
+
version: literal(1),
|
|
8867
|
+
scope: _enum(["draft", "live"]),
|
|
8868
|
+
limits: object({
|
|
8869
|
+
maxValueBytes: number().positive(),
|
|
8870
|
+
maxValues: number().int().positive(),
|
|
8871
|
+
maxSpaces: number().int().positive(),
|
|
8872
|
+
maxIdentities: number().positive(),
|
|
8873
|
+
maxRunWrites: number().positive()
|
|
8874
|
+
}),
|
|
8875
|
+
values: array(object({
|
|
8876
|
+
key: string$1(),
|
|
8877
|
+
size: number().nonnegative(),
|
|
8878
|
+
updatedAt: number(),
|
|
8879
|
+
value: json$4().optional()
|
|
8880
|
+
})),
|
|
8881
|
+
spaces: array(object({
|
|
8882
|
+
space: string$1(),
|
|
8883
|
+
count: number().nonnegative(),
|
|
8884
|
+
pendingCount: number().nonnegative(),
|
|
8885
|
+
reservedCount: number().nonnegative(),
|
|
8886
|
+
updatedAt: number()
|
|
8887
|
+
}))
|
|
8888
|
+
});
|
|
8849
8889
|
function checkJsonDepth(value, depth = 0) {
|
|
8850
8890
|
if (depth > 64) throw new TypeError("Value exceeds the maximum JSON depth.");
|
|
8851
8891
|
if (value != null && typeof value == "object") for (const child of Object.values(value)) checkJsonDepth(child, depth + 1);
|
|
@@ -9134,7 +9174,8 @@ var managedFields = object({
|
|
|
9134
9174
|
flowId: text,
|
|
9135
9175
|
revisionId: text
|
|
9136
9176
|
}),
|
|
9137
|
-
httpRequestExecutorSchema
|
|
9177
|
+
httpRequestExecutorSchema,
|
|
9178
|
+
skipDuplicatesExecutorSchema
|
|
9138
9179
|
])
|
|
9139
9180
|
});
|
|
9140
9181
|
var managed = managedFields.transform(limitDecisionTask);
|
|
@@ -9404,7 +9445,8 @@ var revision = object({
|
|
|
9404
9445
|
literal(9),
|
|
9405
9446
|
literal(10),
|
|
9406
9447
|
literal(11),
|
|
9407
|
-
literal(12)
|
|
9448
|
+
literal(12),
|
|
9449
|
+
literal(13)
|
|
9408
9450
|
]),
|
|
9409
9451
|
document,
|
|
9410
9452
|
modules: record$2(text, module)
|
|
@@ -9605,6 +9647,7 @@ array(union([...new Map(Object.entries(shapes).map(([kind, shape]) => [kind, sha
|
|
|
9605
9647
|
...shape
|
|
9606
9648
|
})])).values()])).min(1);
|
|
9607
9649
|
function checkModelVersion(content) {
|
|
9650
|
+
if (content.modelVersion < 13 && Object.values(content.document.graph.nodes).some((candidateNode) => candidateNode.kind === "task" && "executor" in candidateNode.task && candidateNode.task.executor.kind === "skip-duplicates")) throw new Error("Skip Duplicates requires Flow model v13.");
|
|
9608
9651
|
if (content.modelVersion < 12 && Object.values(content.document.graph.nodes).some((candidateNode) => candidateNode.kind == "task" && "moduleId" in candidateNode.task && candidateNode.task.capabilities?.some((item) => item.kind == "http"))) throw new TypeError("Code HTTP access requires Flow model version 12.");
|
|
9609
9652
|
if (content.modelVersion < 11 && Object.values(content.document.graph.nodes).some((candidateNode) => candidateNode.kind == "task" && "executor" in candidateNode.task && candidateNode.task.executor.kind == "http-request")) throw new TypeError("HTTP Request requires Flow model version 11.");
|
|
9610
9653
|
if (content.modelVersion < 11 && Object.values(content.document.graph.nodes).some((candidateNode) => candidateNode.kind == "task" && ("moduleId" in candidateNode.task ? candidateNode.task.capabilities?.some((item) => item.kind == "workflow") : candidateNode.task.executor.kind == "agent" && candidateNode.task.executor.tools.some((item) => item.kind == "workflow")))) throw new TypeError("Workflow tools require Flow model version 11.");
|
|
@@ -9636,8 +9679,8 @@ function resourceNameIssue(value) {
|
|
|
9636
9679
|
}
|
|
9637
9680
|
//#endregion
|
|
9638
9681
|
//#region src/runtime/common/engineContract.ts
|
|
9639
|
-
/**
|
|
9640
|
-
var currentEngineContract = "open-flow-engine/
|
|
9682
|
+
/** v10 adds persistent Flow State to the published v9 Node compatibility and fetch contract. */
|
|
9683
|
+
var currentEngineContract = "open-flow-engine/v10";
|
|
9641
9684
|
/** The published v8 Node compatibility contract, retained for existing Publications and Runs. */
|
|
9642
9685
|
var nodejsEngineContract = "open-flow-engine/v8/nodejs-compat-v1";
|
|
9643
9686
|
var platformSource = (contract) => `export const engineContract = ${JSON.stringify(contract)}
|
|
@@ -9682,13 +9725,19 @@ var nodejsContract = {
|
|
|
9682
9725
|
].flatMap((name) => [name, `node:${name}`])),
|
|
9683
9726
|
platformSource: platformSource(nodejsEngineContract)
|
|
9684
9727
|
};
|
|
9685
|
-
var
|
|
9728
|
+
var v9Contract = {
|
|
9686
9729
|
...nodejsContract,
|
|
9687
9730
|
codeFetch: true,
|
|
9731
|
+
platformSource: platformSource("open-flow-engine/v9")
|
|
9732
|
+
};
|
|
9733
|
+
var currentContract = {
|
|
9734
|
+
...v9Contract,
|
|
9735
|
+
flowState: true,
|
|
9688
9736
|
platformSource: platformSource(currentEngineContract)
|
|
9689
9737
|
};
|
|
9690
9738
|
function findEngineContract(contract) {
|
|
9691
|
-
if (contract == "open-flow-engine/
|
|
9739
|
+
if (contract == "open-flow-engine/v10") return currentContract;
|
|
9740
|
+
if (contract == "open-flow-engine/v9") return v9Contract;
|
|
9692
9741
|
if (contract == "open-flow-engine/v8") return v8Contract;
|
|
9693
9742
|
if (contract == "open-flow-engine/v8/nodejs-compat-v1") return nodejsContract;
|
|
9694
9743
|
if (contract == "open-flow-engine/v7" || contract == "open-flow-engine/v7/nodejs-compat-v1") return {
|
|
@@ -9755,6 +9804,7 @@ var type = _enum([
|
|
|
9755
9804
|
"decision",
|
|
9756
9805
|
"openapi",
|
|
9757
9806
|
"http-request",
|
|
9807
|
+
"skip-duplicates",
|
|
9758
9808
|
"condition",
|
|
9759
9809
|
"value",
|
|
9760
9810
|
"wait",
|
|
@@ -9885,6 +9935,7 @@ var authoringConfigurations = {
|
|
|
9885
9935
|
"connector": authoringDefinitionSchemas.connector.omit({ outputMode: true }).strict(),
|
|
9886
9936
|
"openapi": authoringOpenApiSchema,
|
|
9887
9937
|
"http-request": httpRequestConfigSchema,
|
|
9938
|
+
"skip-duplicates": skipDuplicatesConfigSchema,
|
|
9888
9939
|
"agent": authoringDefinitionSchemas.agent.omit({
|
|
9889
9940
|
prompt: true,
|
|
9890
9941
|
tools: true
|
|
@@ -10160,11 +10211,14 @@ var controlErrorCode = {
|
|
|
10160
10211
|
triggerKeyInvalid: "trigger-key.invalid",
|
|
10161
10212
|
triggerKeyNotFound: "trigger-key.not-found",
|
|
10162
10213
|
triggerNotFound: "trigger.not-found",
|
|
10214
|
+
tagInvalid: "tag.invalid",
|
|
10215
|
+
tagConflict: "tag.conflict",
|
|
10216
|
+
tagNotFound: "tag.not-found",
|
|
10163
10217
|
variableInvalid: "variable.invalid",
|
|
10164
10218
|
variableLimitReached: "variable.limit-reached",
|
|
10165
10219
|
variableNotFound: "variable.not-found"
|
|
10166
10220
|
};
|
|
10167
|
-
controlErrorCode.eventSourceInvalid, controlErrorCode.eventSourceIdentityUnavailable, controlErrorCode.eventSourceNotFound, controlErrorCode.eventSourceConflict, controlErrorCode.authenticationRequired, controlErrorCode.authorizationDenied, controlErrorCode.bindingUnresolved, controlErrorCode.connectorActionNotFound, controlErrorCode.connectorAccessConflict, controlErrorCode.connectorAccessInvalid, controlErrorCode.connectorAccessRequired, controlErrorCode.connectorAccessUnsupported, controlErrorCode.connectorUnconfigured, controlErrorCode.connectorUnavailable, controlErrorCode.connectorConsoleUnconfigured, controlErrorCode.engineUnavailable, controlErrorCode.engineUnsupported, controlErrorCode.flowInvalid, controlErrorCode.flowRepairRequired, controlErrorCode.flowUpgradeRequired, controlErrorCode.flowNotFound, controlErrorCode.flowBusy, controlErrorCode.flowConflict, controlErrorCode.flowPresentationConflict, controlErrorCode.flowRevisionConflict, controlErrorCode.liveConflict, controlErrorCode.liveNotFound, controlErrorCode.pageInvalidCursor, controlErrorCode.publicationConflict, controlErrorCode.publicationNotFound, controlErrorCode.publicationUnsupported, controlErrorCode.publishOperationNotFound, controlErrorCode.routeNotFound, controlErrorCode.runConflict, controlErrorCode.runEventsExpired, controlErrorCode.runInvalid, controlErrorCode.runNotFound, controlErrorCode.runNotTerminal, controlErrorCode.runOverloaded, controlErrorCode.runWaitNotFound, controlErrorCode.triggerKeyInvalid, controlErrorCode.triggerKeyNotFound, controlErrorCode.triggerNotFound, controlErrorCode.variableInvalid, controlErrorCode.variableLimitReached, controlErrorCode.variableNotFound;
|
|
10221
|
+
controlErrorCode.eventSourceInvalid, controlErrorCode.eventSourceIdentityUnavailable, controlErrorCode.eventSourceNotFound, controlErrorCode.eventSourceConflict, controlErrorCode.authenticationRequired, controlErrorCode.authorizationDenied, controlErrorCode.bindingUnresolved, controlErrorCode.connectorActionNotFound, controlErrorCode.connectorAccessConflict, controlErrorCode.connectorAccessInvalid, controlErrorCode.connectorAccessRequired, controlErrorCode.connectorAccessUnsupported, controlErrorCode.connectorUnconfigured, controlErrorCode.connectorUnavailable, controlErrorCode.connectorConsoleUnconfigured, controlErrorCode.engineUnavailable, controlErrorCode.engineUnsupported, controlErrorCode.flowInvalid, controlErrorCode.flowRepairRequired, controlErrorCode.flowUpgradeRequired, controlErrorCode.flowNotFound, controlErrorCode.flowBusy, controlErrorCode.flowConflict, controlErrorCode.flowPresentationConflict, controlErrorCode.flowRevisionConflict, controlErrorCode.liveConflict, controlErrorCode.liveNotFound, controlErrorCode.pageInvalidCursor, controlErrorCode.publicationConflict, controlErrorCode.publicationNotFound, controlErrorCode.publicationUnsupported, controlErrorCode.publishOperationNotFound, controlErrorCode.routeNotFound, controlErrorCode.runConflict, controlErrorCode.runEventsExpired, controlErrorCode.runInvalid, controlErrorCode.runNotFound, controlErrorCode.runNotTerminal, controlErrorCode.runOverloaded, controlErrorCode.runWaitNotFound, controlErrorCode.triggerKeyInvalid, controlErrorCode.triggerKeyNotFound, controlErrorCode.triggerNotFound, controlErrorCode.tagInvalid, controlErrorCode.tagConflict, controlErrorCode.tagNotFound, controlErrorCode.variableInvalid, controlErrorCode.variableLimitReached, controlErrorCode.variableNotFound;
|
|
10168
10222
|
var ApiError = class extends Error {
|
|
10169
10223
|
constructor(status, code, message, details) {
|
|
10170
10224
|
super(message);
|
|
@@ -11430,6 +11484,7 @@ function flow$1(value) {
|
|
|
11430
11484
|
publicationId: string(target.publicationId),
|
|
11431
11485
|
revisionId: string(target.revisionId)
|
|
11432
11486
|
} },
|
|
11487
|
+
tagIds: source.tagIds === void 0 ? [] : strings(source.tagIds),
|
|
11433
11488
|
createdAt: string(source.createdAt),
|
|
11434
11489
|
...source.connectorTeamId == null ? {} : { connectorTeamId: string(source.connectorTeamId) },
|
|
11435
11490
|
draftRevisionId: string(source.draftRevisionId),
|
|
@@ -11864,6 +11919,33 @@ function randomId() {
|
|
|
11864
11919
|
return `${Date.now().toString(36)}-${Math.random().toString(36).slice(2)}`;
|
|
11865
11920
|
}
|
|
11866
11921
|
//#endregion
|
|
11922
|
+
//#region src/control/common/tags.ts
|
|
11923
|
+
function normalizeFlowQuery(query = {}) {
|
|
11924
|
+
return {
|
|
11925
|
+
query: query.query?.trim().toLowerCase() ?? "",
|
|
11926
|
+
tagIds: [...new Set(query.tagIds ?? [])].toSorted(),
|
|
11927
|
+
untagged: query.untagged ?? false
|
|
11928
|
+
};
|
|
11929
|
+
}
|
|
11930
|
+
function decodeTag(value) {
|
|
11931
|
+
const source = record(value);
|
|
11932
|
+
if (source.version != 1) return invalidResponse();
|
|
11933
|
+
return {
|
|
11934
|
+
tagId: string(source.tagId),
|
|
11935
|
+
name: string(source.name),
|
|
11936
|
+
version: 1
|
|
11937
|
+
};
|
|
11938
|
+
}
|
|
11939
|
+
function decodeTagListItem(value) {
|
|
11940
|
+
const source = record(value);
|
|
11941
|
+
const referenceCount = integer(source.referenceCount);
|
|
11942
|
+
if (referenceCount < 0) return invalidResponse();
|
|
11943
|
+
return {
|
|
11944
|
+
...decodeTag(source),
|
|
11945
|
+
referenceCount
|
|
11946
|
+
};
|
|
11947
|
+
}
|
|
11948
|
+
//#endregion
|
|
11867
11949
|
//#region src/control/common/api.ts
|
|
11868
11950
|
function decodeRunEvent(value) {
|
|
11869
11951
|
const source = record(value);
|
|
@@ -11967,7 +12049,7 @@ function decodeRunEvent(value) {
|
|
|
11967
12049
|
switch (kind) {
|
|
11968
12050
|
case "node.started": {
|
|
11969
12051
|
const nodeKind = payload.nodeKind;
|
|
11970
|
-
if (nodeKind !== void 0 && nodeKind !== "approval" && nodeKind !== "condition" && nodeKind !== "connector" && nodeKind !== "javascript" && nodeKind !== "decision" && nodeKind !== "openapi" && nodeKind !== "http-request" && nodeKind !== "llm" && nodeKind !== "agent" && nodeKind !== "value" && nodeKind !== "outputs" && nodeKind !== "webhook-response" && nodeKind !== "workflow" && nodeKind !== "wait") return invalidResponse();
|
|
12052
|
+
if (nodeKind !== void 0 && nodeKind !== "approval" && nodeKind !== "condition" && nodeKind !== "connector" && nodeKind !== "javascript" && nodeKind !== "decision" && nodeKind !== "openapi" && nodeKind !== "http-request" && nodeKind !== "skip-duplicates" && nodeKind !== "llm" && nodeKind !== "agent" && nodeKind !== "value" && nodeKind !== "outputs" && nodeKind !== "webhook-response" && nodeKind !== "workflow" && nodeKind !== "wait") return invalidResponse();
|
|
11971
12053
|
return {
|
|
11972
12054
|
...base,
|
|
11973
12055
|
kind,
|
|
@@ -12094,6 +12176,10 @@ var ControlClient = class {
|
|
|
12094
12176
|
}
|
|
12095
12177
|
async listFlows(options = {}) {
|
|
12096
12178
|
const parameters = new URLSearchParams();
|
|
12179
|
+
const filter = normalizeFlowQuery(options);
|
|
12180
|
+
if (filter.query) parameters.set("query", filter.query);
|
|
12181
|
+
if (filter.tagIds.length) parameters.set("tagIds", filter.tagIds.join(","));
|
|
12182
|
+
if (filter.untagged) parameters.set("untagged", "true");
|
|
12097
12183
|
if (options.cursor != null) parameters.set("cursor", options.cursor);
|
|
12098
12184
|
if (options.limit != null) parameters.set("limit", String(options.limit));
|
|
12099
12185
|
if (options.includeTotal != null) parameters.set("includeTotal", String(options.includeTotal));
|
|
@@ -12183,15 +12269,18 @@ var ControlClient = class {
|
|
|
12183
12269
|
file,
|
|
12184
12270
|
name: options.name,
|
|
12185
12271
|
teamId: options.teamId,
|
|
12272
|
+
tagIds: options.tagIds,
|
|
12186
12273
|
version: 1
|
|
12187
12274
|
})
|
|
12188
12275
|
}));
|
|
12189
12276
|
}
|
|
12190
|
-
async createFlow(name, idempotencyKey = `flow-${randomId()}`, teamId) {
|
|
12277
|
+
async createFlow(name, idempotencyKey = `flow-${randomId()}`, teamId, tagIds, initialPresentation) {
|
|
12191
12278
|
return flow$1(await this.request("/v1/flows", {
|
|
12192
12279
|
body: JSON.stringify({
|
|
12193
12280
|
name,
|
|
12194
12281
|
...teamId == null ? {} : { teamId },
|
|
12282
|
+
...tagIds == null ? {} : { tagIds },
|
|
12283
|
+
...initialPresentation == null ? {} : { presentation: initialPresentation },
|
|
12195
12284
|
version: 1
|
|
12196
12285
|
}),
|
|
12197
12286
|
headers: { "idempotency-key": idempotencyKey },
|
|
@@ -12226,15 +12315,68 @@ var ControlClient = class {
|
|
|
12226
12315
|
if (source.version != 1 || !Array.isArray(source.listeners)) return invalidResponse();
|
|
12227
12316
|
return source.listeners.map(errorListener);
|
|
12228
12317
|
}
|
|
12229
|
-
async
|
|
12230
|
-
|
|
12318
|
+
async listTags(signal) {
|
|
12319
|
+
const source = record(await this.request("/v1/tags", { signal }));
|
|
12320
|
+
if (source.version != 1 || !Array.isArray(source.tags)) return invalidResponse();
|
|
12321
|
+
return {
|
|
12322
|
+
tags: source.tags.map(decodeTagListItem),
|
|
12323
|
+
version: 1
|
|
12324
|
+
};
|
|
12325
|
+
}
|
|
12326
|
+
async createTag(name) {
|
|
12327
|
+
return decodeTag(await this.request("/v1/tags", {
|
|
12328
|
+
method: "POST",
|
|
12231
12329
|
body: JSON.stringify({
|
|
12232
12330
|
name,
|
|
12233
12331
|
version: 1
|
|
12234
|
-
})
|
|
12235
|
-
|
|
12332
|
+
})
|
|
12333
|
+
}));
|
|
12334
|
+
}
|
|
12335
|
+
async renameTag(tagId, name) {
|
|
12336
|
+
return decodeTag(await this.request(`/v1/tags/${segment(tagId)}`, {
|
|
12337
|
+
method: "PATCH",
|
|
12338
|
+
body: JSON.stringify({
|
|
12339
|
+
name,
|
|
12340
|
+
version: 1
|
|
12341
|
+
})
|
|
12342
|
+
}));
|
|
12343
|
+
}
|
|
12344
|
+
async deleteTag(tagId) {
|
|
12345
|
+
if (record(await this.request(`/v1/tags/${segment(tagId)}`, { method: "DELETE" })).version != 1) invalidResponse();
|
|
12346
|
+
}
|
|
12347
|
+
async setFlowTags(flowId, tagIds) {
|
|
12348
|
+
return flow$1(await this.request(`/v1/flows/${segment(flowId)}/tags`, {
|
|
12349
|
+
method: "PUT",
|
|
12350
|
+
body: JSON.stringify({
|
|
12351
|
+
tagIds,
|
|
12352
|
+
version: 1
|
|
12353
|
+
})
|
|
12236
12354
|
}));
|
|
12237
12355
|
}
|
|
12356
|
+
async updateFlow(flowId, changes) {
|
|
12357
|
+
return flow$1(await this.request(`/v1/flows/${segment(flowId)}`, {
|
|
12358
|
+
method: "PATCH",
|
|
12359
|
+
body: JSON.stringify({
|
|
12360
|
+
...changes,
|
|
12361
|
+
version: 1
|
|
12362
|
+
})
|
|
12363
|
+
}));
|
|
12364
|
+
}
|
|
12365
|
+
async getFlowState(flowId, scope, values = false) {
|
|
12366
|
+
const result = flowStateViewSchema.safeParse(await this.request(`/v1/flows/${segment(flowId)}/state?scope=${scope}&values=${values}`));
|
|
12367
|
+
return result.success && result.data.scope === scope ? result.data : invalidResponse();
|
|
12368
|
+
}
|
|
12369
|
+
async clearFlowState(flowId, scope, key) {
|
|
12370
|
+
const source = record(await this.request(`/v1/flows/${segment(flowId)}/state?scope=${scope}${key == null ? "" : `&key=${encodeURIComponent(key)}`}`, { method: "DELETE" }));
|
|
12371
|
+
if (source.version !== 1 || source.cleared !== true) invalidResponse();
|
|
12372
|
+
}
|
|
12373
|
+
async clearFlowDedupe(flowId, scope, space) {
|
|
12374
|
+
const source = record(await this.request(`/v1/flows/${segment(flowId)}/dedupe?scope=${scope}&space=${encodeURIComponent(space)}`, { method: "DELETE" }));
|
|
12375
|
+
if (source.version !== 1 || source.cleared !== true) invalidResponse();
|
|
12376
|
+
}
|
|
12377
|
+
async renameFlow(flowId, name) {
|
|
12378
|
+
return this.updateFlow(flowId, { name });
|
|
12379
|
+
}
|
|
12238
12380
|
async deleteFlow(flowId) {
|
|
12239
12381
|
return flow$1(await this.request(`/v1/flows/${segment(flowId)}`, { method: "DELETE" }));
|
|
12240
12382
|
}
|
|
@@ -12986,6 +13128,9 @@ function tool(description, schema, readOnly, idempotent = true) {
|
|
|
12986
13128
|
};
|
|
12987
13129
|
}
|
|
12988
13130
|
var mcpTools = {
|
|
13131
|
+
flow_state: tool("Inspect Flow state usage, business keys and deduplication spaces. Values are omitted unless requested. Scope is required.", stateQuerySchema.extend({ flowId: flow }), true),
|
|
13132
|
+
flow_state_clear: tool("Delete one business state key or clear all business values. Explicit draft/live scope is required; live changes production state immediately.", stateClearSchema.extend({ flowId: flow }), false),
|
|
13133
|
+
flow_dedupe_clear: tool("Clear one deduplication space (flow or node:<id>). Explicit draft/live scope is required; live changes production history immediately.", dedupeClearSchema.extend({ flowId: flow }), false),
|
|
12989
13134
|
flow_canvas: tool("Broadcast a transient canvas command to connected Workbenches viewing this Flow. Success only confirms Server broadcast, not delivery or execution. No replay, session selection or Presentation save. Pan uses screen pixels (positive right/down); zoom is an absolute ratio (0.1–3); fit includes all nodes. Repeating pan moves again.", strictObject({
|
|
12990
13135
|
flowId: flow,
|
|
12991
13136
|
command: canvasCommandSchema
|
|
@@ -54,6 +54,7 @@ var nodeKinds = /* @__PURE__ */ new Set([
|
|
|
54
54
|
"javascript",
|
|
55
55
|
"openapi",
|
|
56
56
|
"http-request",
|
|
57
|
+
"skip-duplicates",
|
|
57
58
|
"llm",
|
|
58
59
|
"value",
|
|
59
60
|
"wait",
|
|
@@ -80,12 +81,12 @@ function nodeKind(value) {
|
|
|
80
81
|
function runId(event) {
|
|
81
82
|
return string(event.runId, "Runtime event runId");
|
|
82
83
|
}
|
|
83
|
-
function nodeContext(event, flows, platformRunId) {
|
|
84
|
+
function nodeContext(event, flows, platformRunId, identify) {
|
|
84
85
|
const rawRunId = runId(event);
|
|
85
86
|
const flowId = flows.get(rawRunId);
|
|
86
87
|
if (flowId == null) throw new TypeError("Runtime node event preceded its run.started event.");
|
|
87
88
|
return {
|
|
88
|
-
executionId:
|
|
89
|
+
executionId: identify("execution", platformRunId, rawRunId, string(event.jobId, "Runtime node event jobId")),
|
|
89
90
|
flowId,
|
|
90
91
|
nodeId: string(event.nodeId, "Runtime node event nodeId"),
|
|
91
92
|
rawRunId
|
|
@@ -138,6 +139,16 @@ function createEventProjector(platformRunId, nodeFailureCodes) {
|
|
|
138
139
|
const jobs = /* @__PURE__ */ new Map();
|
|
139
140
|
const nodeProgressBuckets = /* @__PURE__ */ new Map();
|
|
140
141
|
const runProgressBuckets = /* @__PURE__ */ new Map();
|
|
142
|
+
const identities = /* @__PURE__ */ new Map();
|
|
143
|
+
const identify = (prefix, ...parts) => {
|
|
144
|
+
const key = JSON.stringify([prefix, ...parts]);
|
|
145
|
+
let identity = identities.get(key);
|
|
146
|
+
if (identity == null) {
|
|
147
|
+
identity = opaqueId(prefix, ...parts);
|
|
148
|
+
identities.set(key, identity);
|
|
149
|
+
}
|
|
150
|
+
return identity;
|
|
151
|
+
};
|
|
141
152
|
return async (value) => {
|
|
142
153
|
const event = object(value, "Runtime event");
|
|
143
154
|
const type = string(event.type, "Runtime event type");
|
|
@@ -156,8 +167,8 @@ function createEventProjector(platformRunId, nodeFailureCodes) {
|
|
|
156
167
|
kind: "run.started",
|
|
157
168
|
payload: {
|
|
158
169
|
flowId,
|
|
159
|
-
...parentRunId === void 0 ? {} : { parentScopeId: await
|
|
160
|
-
scopeId: await
|
|
170
|
+
...parentRunId === void 0 ? {} : { parentScopeId: await identify("scope", platformRunId, parentRunId) },
|
|
171
|
+
scopeId: await identify("scope", platformRunId, rawRunId)
|
|
161
172
|
}
|
|
162
173
|
};
|
|
163
174
|
}
|
|
@@ -174,7 +185,7 @@ function createEventProjector(platformRunId, nodeFailureCodes) {
|
|
|
174
185
|
payload: {
|
|
175
186
|
flowId,
|
|
176
187
|
progress: event.progress,
|
|
177
|
-
scopeId: await
|
|
188
|
+
scopeId: await identify("scope", platformRunId, rawRunId)
|
|
178
189
|
}
|
|
179
190
|
};
|
|
180
191
|
}
|
|
@@ -182,7 +193,7 @@ function createEventProjector(platformRunId, nodeFailureCodes) {
|
|
|
182
193
|
const rawRunId = runId(event);
|
|
183
194
|
if (type == "run.failed" && rawRunId == platformRunId && event.failure != null) {
|
|
184
195
|
const failure = object(event.failure, "Runtime terminal failure");
|
|
185
|
-
const context = nodeContext(failure, flows, platformRunId);
|
|
196
|
+
const context = nodeContext(failure, flows, platformRunId, identify);
|
|
186
197
|
return {
|
|
187
198
|
kind: "node.failed",
|
|
188
199
|
payload: {
|
|
@@ -200,13 +211,13 @@ function createEventProjector(platformRunId, nodeFailureCodes) {
|
|
|
200
211
|
return;
|
|
201
212
|
}
|
|
202
213
|
if (type == "node.started" || type == "node.progress" || type == "node.artifact" || type == "node.log" || type == "node.completed" || type == "node.failed") {
|
|
203
|
-
const context = nodeContext(event, flows, platformRunId);
|
|
214
|
+
const context = nodeContext(event, flows, platformRunId, identify);
|
|
204
215
|
const executionId = await context.executionId;
|
|
205
216
|
const payload = {
|
|
206
217
|
executionId,
|
|
207
218
|
flowId: context.flowId,
|
|
208
219
|
nodeId: context.nodeId,
|
|
209
|
-
scopeId: await
|
|
220
|
+
scopeId: await identify("scope", platformRunId, context.rawRunId),
|
|
210
221
|
...event.systemOutputs === void 0 ? {} : { systemOutputs: object(event.systemOutputs, "Runtime system outputs") },
|
|
211
222
|
...event.handled === true ? { handled: true } : {}
|
|
212
223
|
};
|
|
@@ -1,5 +1,19 @@
|
|
|
1
1
|
import type { CodeModule, ConnectorCapability, TaskCapability, JsonValue } from './flow-model.js';
|
|
2
2
|
export { currentEngineContract, nodejsEngineContract, findEngineContract, type EngineContract } from './engine-contract.js';
|
|
3
|
+
/** Serialized into the guest; keep validation and helpers self-contained. */
|
|
4
|
+
export declare function createState(invoke: (kind: string, payload: JsonValue) => Promise<RuntimeCapabilityResponse>): {
|
|
5
|
+
state: Readonly<{
|
|
6
|
+
get(key: unknown): Promise<JsonValue>;
|
|
7
|
+
set(key: unknown, value: unknown): Promise<void>;
|
|
8
|
+
insert(key: unknown, value: unknown): Promise<boolean>;
|
|
9
|
+
delete(key: unknown): Promise<void>;
|
|
10
|
+
list(): Promise<string[]>;
|
|
11
|
+
}>;
|
|
12
|
+
dedupe: Readonly<{
|
|
13
|
+
insert(ids: unknown): Promise<boolean[]>;
|
|
14
|
+
has(ids: unknown): Promise<boolean[]>;
|
|
15
|
+
}>;
|
|
16
|
+
};
|
|
3
17
|
export type RuntimeModule = Pick<CodeModule, 'imports' | 'source'>;
|
|
4
18
|
/** Snapshot a Task result before JSON transport can discard or coerce invalid values. */
|
|
5
19
|
export declare function snapshotRuntimeResult(value: unknown): JsonValue | undefined;
|