@oomol-lab/open-flow 0.1.0-beta.50 → 0.1.0-beta.52

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.
Files changed (44) hide show
  1. package/dist/browser/{createResourceDialog-CSltk-qY.js → createResourceDialog-BsaBMf7_.js} +2 -1
  2. package/dist/browser/flow-authoring-node.d.ts +3 -1
  3. package/dist/browser/flow-authoring.js +82 -3
  4. package/dist/browser/flow-change-schema.d.ts +1 -1
  5. package/dist/browser/flow-change.d.ts +15 -2
  6. package/dist/browser/flow-change.js +81 -3
  7. package/dist/browser/{flowChanges-DbYrpHnS.js → flowChanges-DtraMpva.js} +3858 -1921
  8. package/dist/browser/{flowWorkspace-CjwpbVBR.js → flowWorkspace-DLgti4Lk.js} +1353 -513
  9. package/dist/browser/{workbenchSelect-oVujN2z6.js → icons-0s-Q_3lp.js} +92 -35
  10. package/dist/browser/licenses.md +204 -0
  11. package/dist/browser/preview.css +302 -179
  12. package/dist/browser/preview.js +4829 -2198
  13. package/dist/browser/theme.css +2 -0
  14. package/dist/browser/ui-hostNavigationActions.d.ts +13 -0
  15. package/dist/browser/ui-hostTooltip.d.ts +8 -0
  16. package/dist/browser/ui-logo.d.ts +5 -0
  17. package/dist/browser/ui.css +102 -8
  18. package/dist/browser/ui.d.ts +3 -0
  19. package/dist/browser/ui.js +176 -11
  20. package/dist/browser/workbench-contract.d.ts +5 -11
  21. package/dist/browser/workbench.css +366 -200
  22. package/dist/browser/workbench.d.ts +1 -1
  23. package/dist/browser/workbench.js +1154 -379
  24. package/dist/browser/workbenchSelect-BqUPacsr.js +31 -0
  25. package/dist/common/authoringExamples.d.ts +4 -2
  26. package/dist/common/control-api-conformance.js +129 -11
  27. package/dist/common/control-api.d.ts +38 -5
  28. package/dist/common/control-api.js +198 -12
  29. package/dist/common/control-requests.d.ts +4 -0
  30. package/dist/common/control-requests.js +1320 -67
  31. package/dist/common/flow-encoding.js +64 -5
  32. package/dist/common/flow-semantics.js +823 -316
  33. package/dist/common/integration-trigger.js +39 -1
  34. package/dist/common/mcp.js +129 -11
  35. package/dist/common/openapi.d.ts +53 -0
  36. package/dist/common/openapi.js +10390 -0
  37. package/dist/common/poll-trigger.js +39 -1
  38. package/dist/common/provider-triggers.js +39 -1
  39. package/dist/common/run-events.js +26 -1
  40. package/dist/common/scheduler.d.ts +4 -1
  41. package/dist/common/scheduler.js +122 -6
  42. package/dist/common/trigger-contract.d.ts +2 -0
  43. package/dist/common/webhook-trigger.js +39 -1
  44. package/package.json +5 -1
@@ -0,0 +1,31 @@
1
+ import { Ir as cn, ct as SelectContent, ft as SelectTrigger, lt as SelectGroup, ot as Select, pt as SelectValue, ut as SelectItem } from "./icons-0s-Q_3lp.js";
2
+ import { jsx, jsxs } from "react/jsx-runtime";
3
+ //#region src/workbench/browser/runtime/shell/workbenchSelect.tsx
4
+ function WorkbenchSelect({ ariaLabel, className, disabled = false, id, onValueChange, options, portalRoot, size, value, variant }) {
5
+ return /* @__PURE__ */ jsxs(Select, {
6
+ disabled,
7
+ onValueChange: (next) => {
8
+ if (next != null) onValueChange(next);
9
+ },
10
+ value,
11
+ children: [/* @__PURE__ */ jsx(SelectTrigger, {
12
+ "aria-label": ariaLabel,
13
+ className: cn("min-w-32", className),
14
+ id,
15
+ size,
16
+ variant,
17
+ children: /* @__PURE__ */ jsx(SelectValue, { children: options.find((option) => option.value == value)?.label ?? value })
18
+ }), /* @__PURE__ */ jsx(SelectContent, {
19
+ align: "end",
20
+ alignItemWithTrigger: false,
21
+ container: portalRoot,
22
+ children: /* @__PURE__ */ jsx(SelectGroup, { children: options.map((option) => /* @__PURE__ */ jsx(SelectItem, {
23
+ disabled: option.disabled,
24
+ value: option.value,
25
+ children: option.label
26
+ }, option.value)) })
27
+ })]
28
+ });
29
+ }
30
+ //#endregion
31
+ export { WorkbenchSelect as t };
@@ -1,10 +1,12 @@
1
1
  import type { DraftOperation } from './draftOperations.js';
2
2
  declare const descriptions: {
3
3
  readonly manual: 'A Manual start node.';
4
+ readonly error: 'A Flow Error node. Select upstream Flows, then publish and enable this Flow to listen for failures in their automatic runs.';
4
5
  readonly webhook: 'A Webhook start node.';
5
6
  readonly cron: 'An hourly scheduled start node.';
6
7
  readonly poll: 'Gmail polling by key; replace CONNECTION_ID with an active Gmail connection.';
7
8
  readonly integration: 'Telegram webhook integration by key; replace CONNECTION_ID with an active Telegram connection.';
9
+ readonly openapi: 'A fixed JSON API operation. Replace the example document and URL before running.';
8
10
  readonly connector: 'A Connector Task and its node. Replace ACTION_ID, CONNECTION_ID and port definitions using connector_get / connector show.';
9
11
  readonly code: 'A JavaScript module and its node. Use Code for custom computation; use Connector Tasks for existing actions.';
10
12
  readonly condition: 'A condition with true and false execution branches.';
@@ -18,8 +20,8 @@ declare const descriptions: {
18
20
  };
19
21
  export declare const authoringExampleNames: (keyof typeof descriptions)[];
20
22
  export declare const authoringExamples: {
21
- name: "agent" | "approval" | "code" | "condition" | "connector" | "cron" | "integration" | "llm-chat" | "llm-json" | "manual" | "poll" | "poll-notification" | "value" | "wait" | "webhook";
22
- description: "A Connector Task and its node. Replace ACTION_ID, CONNECTION_ID and port definitions using connector_get / connector show." | "A JavaScript module and its node. Use Code for custom computation; use Connector Tasks for existing actions." | "A Manual start node." | "A Wait with a continue action and a built-in notification output." | "A Webhook start node." | "A condition with true and false execution branches." | "A fixed value node." | "An Agent with code computation enabled. Configure a model available in the deployment." | "An Approval with approve and reject decision branches and a built-in notification output." | "An LLM JSON Task and its node; configure a model available in the deployment." | "An LLM chat Task and its node; configure a model available in the deployment." | "An hourly scheduled start node." | "Gmail events → JavaScript text formatting → Connector notification. Replace connection/action IDs and match the notification input ports." | "Gmail polling by key; replace CONNECTION_ID with an active Gmail connection." | "Telegram webhook integration by key; replace CONNECTION_ID with an active Telegram connection.";
23
+ name: "agent" | "approval" | "code" | "condition" | "connector" | "cron" | "error" | "integration" | "llm-chat" | "llm-json" | "manual" | "openapi" | "poll" | "poll-notification" | "value" | "wait" | "webhook";
24
+ description: "A Connector Task and its node. Replace ACTION_ID, CONNECTION_ID and port definitions using connector_get / connector show." | "A Flow Error node. Select upstream Flows, then publish and enable this Flow to listen for failures in their automatic runs." | "A JavaScript module and its node. Use Code for custom computation; use Connector Tasks for existing actions." | "A Manual start node." | "A Wait with a continue action and a built-in notification output." | "A Webhook start node." | "A condition with true and false execution branches." | "A fixed JSON API operation. Replace the example document and URL before running." | "A fixed value node." | "An Agent with code computation enabled. Configure a model available in the deployment." | "An Approval with approve and reject decision branches and a built-in notification output." | "An LLM JSON Task and its node; configure a model available in the deployment." | "An LLM chat Task and its node; configure a model available in the deployment." | "An hourly scheduled start node." | "Gmail events → JavaScript text formatting → Connector notification. Replace connection/action IDs and match the notification input ports." | "Gmail polling by key; replace CONNECTION_ID with an active Gmail connection." | "Telegram webhook integration by key; replace CONNECTION_ID with an active Telegram connection.";
23
25
  }[];
24
26
  export declare function authoringExample(name: string): {
25
27
  version: 1;
@@ -5799,6 +5799,15 @@ function json$3(params) {
5799
5799
  });
5800
5800
  return jsonSchema;
5801
5801
  }
5802
+ //#endregion
5803
+ //#region src/openapi/common/authBindings.ts
5804
+ /** Never allow credentials to enter a Revision as literal node inputs. */
5805
+ function assertOpenApiAuthBindings(document) {
5806
+ for (const graph of [document.graph, ...Object.values(document.subflows).map((subflow) => subflow.graph)]) for (const node of Object.values(graph.nodes)) {
5807
+ if (node.kind != "task" || node.taskId == null || document.tasks[node.taskId]?.executor.kind != "openapi") continue;
5808
+ for (const [handle, mapping] of Object.entries(node.inputs)) if (handle.startsWith("auth.") && (mapping.kind == "value" || mapping.kind == "sources" && mapping.sources.some((source) => source.kind == "flow"))) throw new TypeError("OpenAPI authentication accepts deployment variables and upstream outputs only.");
5809
+ }
5810
+ }
5802
5811
  function checkJsonDepth(value, depth = 0) {
5803
5812
  if (depth > 64) throw new TypeError("Value exceeds the maximum JSON depth.");
5804
5813
  if (value != null && typeof value == "object") for (const child of Object.values(value)) checkJsonDepth(child, depth + 1);
@@ -5929,6 +5938,24 @@ var managed = object({
5929
5938
  action: text,
5930
5939
  connectionId: text.optional()
5931
5940
  }),
5941
+ object({
5942
+ kind: literal("openapi"),
5943
+ sourceUrl: text,
5944
+ method: text,
5945
+ path: text,
5946
+ serverUrl: text,
5947
+ document: json$2,
5948
+ auth: array(object({
5949
+ id: text,
5950
+ type: _enum([
5951
+ "bearer",
5952
+ "basic",
5953
+ "apiKey"
5954
+ ]),
5955
+ name: text.optional(),
5956
+ in: _enum(["header", "query"]).optional()
5957
+ }))
5958
+ }),
5932
5959
  object({
5933
5960
  kind: literal("llm"),
5934
5961
  mode: _enum(["chat", "json"])
@@ -6045,6 +6072,7 @@ var endpoint = object({
6045
6072
  ])),
6046
6073
  successStatus: number()
6047
6074
  });
6075
+ var sourceFlowIds = array(text.min(1)).refine((ids) => new Set(ids).size === ids.length, "Duplicate source Flow ID.");
6048
6076
  var trigger = {
6049
6077
  name: text,
6050
6078
  description: text.optional(),
@@ -6102,6 +6130,11 @@ var node = union([
6102
6130
  ...trigger,
6103
6131
  kind: literal("manual")
6104
6132
  }),
6133
+ strictObject({
6134
+ ...trigger,
6135
+ kind: literal("error"),
6136
+ sourceFlowIds: sourceFlowIds.optional()
6137
+ }),
6105
6138
  object({
6106
6139
  ...trigger,
6107
6140
  kind: literal("webhook"),
@@ -6173,7 +6206,11 @@ var document = object({
6173
6206
  tasks: record$1(text, managed)
6174
6207
  });
6175
6208
  var revision = object({
6176
- modelVersion: union([literal(2), literal(4)]),
6209
+ modelVersion: union([
6210
+ literal(2),
6211
+ literal(4),
6212
+ literal(5)
6213
+ ]),
6177
6214
  document,
6178
6215
  modules: record$1(text, module)
6179
6216
  });
@@ -6183,9 +6220,17 @@ revision.extend({
6183
6220
  });
6184
6221
  function decodeRevisionContent(value) {
6185
6222
  checkJsonDepth(value);
6186
- return revision.parse(value);
6223
+ const content = revision.parse(value);
6224
+ checkErrorModelVersion(content);
6225
+ assertOpenApiAuthBindings(content.document);
6226
+ return content;
6187
6227
  }
6188
6228
  var shapes = {
6229
+ "graph.trigger.sources.set": {
6230
+ nodeId: text,
6231
+ before: sourceFlowIds.optional(),
6232
+ value: sourceFlowIds.optional()
6233
+ },
6189
6234
  "binding.create": {
6190
6235
  bindingId: text,
6191
6236
  binding
@@ -6339,6 +6384,11 @@ var shapes = {
6339
6384
  before: text.optional(),
6340
6385
  value: text.optional()
6341
6386
  },
6387
+ "task.openapi.set": {
6388
+ taskId: text,
6389
+ before: managed,
6390
+ value: managed
6391
+ },
6342
6392
  "task.agent.set": {
6343
6393
  taskId: text,
6344
6394
  before: managed,
@@ -6359,6 +6409,9 @@ array(union([...new Map(Object.entries(shapes).map(([kind, shape]) => [kind, sha
6359
6409
  kind: literal(kind),
6360
6410
  ...shape
6361
6411
  })])).values()])).min(1);
6412
+ function checkErrorModelVersion(content) {
6413
+ if (content.modelVersion < 5 && [content.document.graph, ...Object.values(content.document.subflows).map((item) => item.graph)].some((item) => Object.values(item.nodes).some((itemNode) => itemNode.kind == "error"))) throw new TypeError("Error workflows require Flow model version 5.");
6414
+ }
6362
6415
  //#endregion
6363
6416
  //#region src/flow/common/change.ts
6364
6417
  var schemaKeywords = /* @__PURE__ */ new Set([
@@ -9621,6 +9674,7 @@ function triggerKey(value) {
9621
9674
  };
9622
9675
  }
9623
9676
  var triggerKinds = /* @__PURE__ */ new Set([
9677
+ "error",
9624
9678
  "cron",
9625
9679
  "integration",
9626
9680
  "poll",
@@ -9959,6 +10013,7 @@ function flow(value) {
9959
10013
  revisionId: string$1(target.revisionId)
9960
10014
  } },
9961
10015
  createdAt: string$1(source.createdAt),
10016
+ ...source.connectorTeamId == null ? {} : { connectorTeamId: string$1(source.connectorTeamId) },
9962
10017
  draftRevisionId: string$1(source.draftRevisionId),
9963
10018
  flowId: string$1(source.flowId),
9964
10019
  name: string$1(source.name),
@@ -10003,6 +10058,17 @@ function variable(value) {
10003
10058
  version: 1
10004
10059
  };
10005
10060
  }
10061
+ function errorListener(value) {
10062
+ const source = record$2(value);
10063
+ if (typeof source.enabled != "boolean") return invalidResponse();
10064
+ return {
10065
+ flowId: string$1(source.flowId),
10066
+ flowName: string$1(source.flowName),
10067
+ nodeId: string$1(source.nodeId),
10068
+ nodeName: string$1(source.nodeName),
10069
+ enabled: source.enabled
10070
+ };
10071
+ }
10006
10072
  //#endregion
10007
10073
  //#region src/control/common/publicationDecoders.ts
10008
10074
  function publication(value) {
@@ -10272,6 +10338,7 @@ function runDetails(value) {
10272
10338
  };
10273
10339
  const details = {
10274
10340
  ...summary,
10341
+ ...errorHandling(source),
10275
10342
  closureDigest: string$1(source.closureDigest),
10276
10343
  engineContract: string$1(source.engineContract),
10277
10344
  engineDigest: string$1(source.engineDigest),
@@ -10371,10 +10438,7 @@ function runResult(value) {
10371
10438
  const error = record$2(source.error);
10372
10439
  return {
10373
10440
  ...base,
10374
- error: {
10375
- code: string$1(error.code),
10376
- message: string$1(error.message)
10377
- },
10441
+ error: runFailure(error),
10378
10442
  status: "failed"
10379
10443
  };
10380
10444
  }
@@ -10382,15 +10446,52 @@ function runResult(value) {
10382
10446
  const error = record$2(source.error);
10383
10447
  return {
10384
10448
  ...base,
10385
- error: {
10386
- code: string$1(error.code),
10387
- message: string$1(error.message)
10388
- },
10449
+ error: runFailure(error),
10389
10450
  status: "indeterminate"
10390
10451
  };
10391
10452
  }
10392
10453
  return invalidResponse();
10393
10454
  }
10455
+ function errorHandling(source) {
10456
+ const errorSource = source.errorSource == null ? void 0 : record$2(source.errorSource);
10457
+ if (source.errorDispatches != null && !Array.isArray(source.errorDispatches)) return invalidResponse();
10458
+ return {
10459
+ ...errorSource == null ? {} : { errorSource: {
10460
+ flowId: string$1(errorSource.flowId),
10461
+ runId: string$1(errorSource.runId)
10462
+ } },
10463
+ ...source.errorDispatches == null ? {} : { errorDispatches: source.errorDispatches.map((value) => {
10464
+ const dispatch = record$2(value);
10465
+ const flowId = string$1(dispatch.flowId);
10466
+ switch (dispatch.status) {
10467
+ case "pending": return {
10468
+ status: "pending",
10469
+ flowId
10470
+ };
10471
+ case "dispatched": return {
10472
+ status: "dispatched",
10473
+ flowId,
10474
+ runId: string$1(dispatch.runId)
10475
+ };
10476
+ case "failed": return {
10477
+ status: "failed",
10478
+ flowId,
10479
+ message: string$1(dispatch.message)
10480
+ };
10481
+ default: return invalidResponse();
10482
+ }
10483
+ }) }
10484
+ };
10485
+ }
10486
+ function runFailure(error) {
10487
+ return {
10488
+ code: string$1(error.code),
10489
+ message: string$1(error.message),
10490
+ ...error.nodeId === void 0 ? {} : { nodeId: string$1(error.nodeId) },
10491
+ ...error.jobId === void 0 ? {} : { jobId: string$1(error.jobId) },
10492
+ ...error.path === void 0 ? {} : { path: (Array.isArray(error.path) ? error.path : invalidResponse()).map(string$1) }
10493
+ };
10494
+ }
10394
10495
  //#endregion
10395
10496
  //#region src/control/common/random.ts
10396
10497
  function randomId() {
@@ -10505,7 +10606,7 @@ function decodeRunEvent(value) {
10505
10606
  switch (kind) {
10506
10607
  case "node.started": {
10507
10608
  const nodeKind = payload.nodeKind;
10508
- if (nodeKind !== void 0 && nodeKind !== "approval" && nodeKind !== "condition" && nodeKind !== "connector" && nodeKind !== "javascript" && nodeKind !== "llm" && nodeKind !== "agent" && nodeKind !== "subflow" && nodeKind !== "value" && nodeKind !== "wait") return invalidResponse();
10609
+ if (nodeKind !== void 0 && nodeKind !== "approval" && nodeKind !== "condition" && nodeKind !== "connector" && nodeKind !== "javascript" && nodeKind !== "openapi" && nodeKind !== "llm" && nodeKind !== "agent" && nodeKind !== "subflow" && nodeKind !== "value" && nodeKind !== "wait") return invalidResponse();
10509
10610
  return {
10510
10611
  ...base,
10511
10612
  kind,
@@ -10614,6 +10715,18 @@ var ControlClient = class {
10614
10715
  constructor(requestControl) {
10615
10716
  this.requestControl = requestControl;
10616
10717
  }
10718
+ async loadOpenApiDocument(url, signal) {
10719
+ const result = record$2(await this.request("/v1/openapi/document", {
10720
+ method: "POST",
10721
+ body: JSON.stringify({
10722
+ url,
10723
+ version: 1
10724
+ }),
10725
+ signal
10726
+ }));
10727
+ if (result.version != 1) return invalidResponse();
10728
+ return jsonValue(result.document);
10729
+ }
10617
10730
  async listFlows(options = {}) {
10618
10731
  const parameters = new URLSearchParams();
10619
10732
  if (options.cursor != null) parameters.set("cursor", options.cursor);
@@ -10689,6 +10802,11 @@ var ControlClient = class {
10689
10802
  async getFlow(flowId) {
10690
10803
  return flow(await this.request(`/v1/flows/${segment(flowId)}`));
10691
10804
  }
10805
+ async getErrorListeners(flowId, signal) {
10806
+ const source = record$2(await this.request(`/v1/flows/${segment(flowId)}/error-listeners`, { signal }));
10807
+ if (source.version != 1 || !Array.isArray(source.listeners)) return invalidResponse();
10808
+ return source.listeners.map(errorListener);
10809
+ }
10692
10810
  async renameFlow(flowId, name) {
10693
10811
  return flow(await this.request(`/v1/flows/${segment(flowId)}`, {
10694
10812
  body: JSON.stringify({
@@ -24,6 +24,13 @@ export type { RunStatus } from './run-lifecycle.js';
24
24
  export { ApiError, controlErrorCode, controlErrorMetadata, type ControlErrorCode } from './control-api-errors.js';
25
25
  export type { FlowCatalogEvent, FlowChangeEvent } from './flow-notifications.js';
26
26
  export type ControlRequest = (path: string, init?: RequestInit) => Promise<Response>;
27
+ export interface ErrorListener {
28
+ readonly flowId: string;
29
+ readonly flowName: string;
30
+ readonly nodeId: string;
31
+ readonly nodeName: string;
32
+ readonly enabled: boolean;
33
+ }
27
34
  export interface Flow {
28
35
  readonly live?: {
29
36
  readonly enabled: boolean;
@@ -33,6 +40,8 @@ export interface Flow {
33
40
  readonly createdAt: string;
34
41
  readonly draftRevisionId: string;
35
42
  readonly flowId: string;
43
+ /** Connector Team scope used by the OOMOL resource cache. */
44
+ readonly connectorTeamId?: string;
36
45
  readonly name: string;
37
46
  readonly status: 'active' | 'retiring';
38
47
  readonly updatedAt: string;
@@ -78,7 +87,7 @@ export interface TriggerBinding {
78
87
  readonly endpointUrl?: string;
79
88
  readonly flowId: string;
80
89
  readonly health: 'failed' | 'healthy' | 'initializing' | 'needs_reauth' | 'suspended';
81
- readonly kind: 'cron' | 'integration' | 'poll' | 'webhook';
90
+ readonly kind: 'error' | 'cron' | 'integration' | 'poll' | 'webhook';
82
91
  readonly lastErrorCode?: string;
83
92
  readonly operatorState: 'active' | 'paused';
84
93
  readonly runtimeVersion: number;
@@ -336,7 +345,24 @@ export interface RunWait {
336
345
  readonly waitId: string;
337
346
  readonly waitingSince: string;
338
347
  }
348
+ export type ErrorDispatch = {
349
+ readonly status: 'pending';
350
+ readonly flowId: string;
351
+ } | {
352
+ readonly status: 'dispatched';
353
+ readonly flowId: string;
354
+ readonly runId: string;
355
+ } | {
356
+ readonly status: 'failed';
357
+ readonly flowId: string;
358
+ readonly message: string;
359
+ };
339
360
  type RunDetailsBase = Run & {
361
+ readonly errorDispatches?: readonly ErrorDispatch[];
362
+ readonly errorSource?: {
363
+ readonly flowId: string;
364
+ readonly runId: string;
365
+ };
340
366
  readonly closureDigest: string;
341
367
  readonly engineContract: string;
342
368
  readonly engineDigest: string;
@@ -364,6 +390,7 @@ export interface RunPage {
364
390
  }
365
391
  export type RunEvent = Readonly<ReturnType<typeof decodeRunEvent>>;
366
392
  export type RunEventKind = RunEvent['kind'];
393
+ export declare function isRunTerminalEvent(event: RunEvent | undefined): boolean;
367
394
  export interface RunEvents {
368
395
  readonly done: boolean;
369
396
  readonly events: readonly RunEvent[];
@@ -379,6 +406,13 @@ export interface RunCancellation {
379
406
  readonly status: Extract<RunStatus, 'canceled' | 'completed' | 'failed' | 'indeterminate'>;
380
407
  readonly version: 1;
381
408
  }
409
+ export interface RunFailure {
410
+ readonly code: string;
411
+ readonly message: string;
412
+ readonly nodeId?: string;
413
+ readonly jobId?: string;
414
+ readonly path?: readonly string[];
415
+ }
382
416
  export type RunResult = {
383
417
  readonly finishedAt: string;
384
418
  readonly result: JsonValue;
@@ -386,10 +420,7 @@ export type RunResult = {
386
420
  readonly status: 'completed';
387
421
  readonly version: 1;
388
422
  } | {
389
- readonly error: {
390
- readonly code: string;
391
- readonly message: string;
392
- };
423
+ readonly error: RunFailure;
393
424
  readonly finishedAt: string;
394
425
  readonly runId: string;
395
426
  readonly status: 'failed' | 'indeterminate';
@@ -691,6 +722,7 @@ export type ConditionalResult<T> = {
691
722
  export declare class ControlClient {
692
723
  private readonly requestControl;
693
724
  constructor(requestControl: ControlRequest);
725
+ loadOpenApiDocument(url: string, signal?: AbortSignal): Promise<JsonValue>;
694
726
  listFlows(options?: {
695
727
  readonly cursor?: string;
696
728
  readonly includeTotal?: boolean;
@@ -714,6 +746,7 @@ export declare class ControlClient {
714
746
  deleteVariable(name: string): Promise<void>;
715
747
  createFlow(name: string, idempotencyKey?: string, teamId?: string): Promise<Flow>;
716
748
  getFlow(flowId: string): Promise<Flow>;
749
+ getErrorListeners(flowId: string, signal?: AbortSignal): Promise<readonly ErrorListener[]>;
717
750
  renameFlow(flowId: string, name: string): Promise<Flow>;
718
751
  deleteFlow(flowId: string): Promise<Flow>;
719
752
  listTriggerKeys(signal?: AbortSignal, locale?: string): Promise<readonly TriggerKeySummary[]>;