@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.
Files changed (74) hide show
  1. package/README.md +3 -0
  2. package/dist/browser/{ContentIcon-Cm1hbVzW.js → ContentIcon-CMn0c-kl.js} +99 -6
  3. package/dist/browser/{FlowCanvas-NzKtla_c.js → FlowCanvas-BQGBcfoL.js} +1709 -613
  4. package/dist/browser/{createResourceDialog-BgdedQqu.js → createResourceDialog-DCGxfKFM.js} +63 -57
  5. package/dist/browser/{dialog-aSElFFw2.js → dialog-WzR4CRFH.js} +76 -77
  6. package/dist/browser/{exportSvg-Dcz4HTo_.js → exportSvg-CYwyYiuH.js} +2 -2
  7. package/dist/browser/{flowChanges-NZyS7HSp.js → flowChanges-Bz4dbDN_.js} +6875 -11091
  8. package/dist/browser/{flowWorkspace-Bl0SDehy.js → flowWorkspace-BI6L6a4r.js} +1415 -3037
  9. package/dist/browser/licenses.md +1 -1
  10. package/dist/browser/preview.css +619 -462
  11. package/dist/browser/preview.js +9016 -14956
  12. package/dist/browser/theme.css +4 -2
  13. package/dist/browser/{tooltip-3XMK9jkr.js → tooltip-BDcVTNpu.js} +65 -2
  14. package/dist/browser/{typeScriptSession-C9sBGOKZ.js → typeScriptSession-CRoezJPN.js} +1 -1
  15. package/dist/browser/ui.css +112 -24
  16. package/dist/browser/ui.js +3 -2
  17. package/dist/browser/workbench.css +10020 -9842
  18. package/dist/browser/workbench.d.ts +5 -2
  19. package/dist/browser/workbench.js +2382 -2668
  20. package/dist/browser/{workbenchSelect-DBGP7Y4Z.js → workbenchSelect-DtAd0zc4.js} +2 -2
  21. package/dist/command/index.js +48 -48
  22. package/dist/common/authoring.d.ts +4 -4
  23. package/dist/common/authoringExamples.d.ts +3 -2
  24. package/dist/common/authoringSchema.d.ts +15 -4
  25. package/dist/common/control-api-conformance.js +155 -15
  26. package/dist/common/control-api-errors.d.ts +12 -0
  27. package/dist/common/control-api.d.ts +39 -2
  28. package/dist/common/control-api.js +180 -37
  29. package/dist/common/control-requests.d.ts +23 -3
  30. package/dist/common/control-requests.js +141 -14
  31. package/dist/common/engine-contract.d.ts +3 -2
  32. package/dist/common/flow-authoring.js +47 -7
  33. package/dist/common/flow-change-schema.d.ts +1 -1
  34. package/dist/common/flow-change.d.ts +2 -2
  35. package/dist/common/flow-change.js +48 -8
  36. package/dist/common/flow-encoding.js +47 -7
  37. package/dist/common/flow-semantics.js +86 -8
  38. package/dist/common/flow-state.d.ts +100 -0
  39. package/dist/common/flow-state.js +5794 -0
  40. package/dist/common/mcp.d.ts +96 -3
  41. package/dist/common/mcp.js +158 -13
  42. package/dist/common/run-events.js +19 -8
  43. package/dist/common/runtime-contract.d.ts +14 -0
  44. package/dist/common/runtime-contract.js +124 -17
  45. package/dist/common/runtime-nodejs-compat.js +11 -12
  46. package/dist/common/scheduler-node-execution.d.ts +1 -0
  47. package/dist/common/scheduler.d.ts +2 -1
  48. package/dist/common/scheduler.js +95 -40
  49. package/dist/common/state-conformance.d.ts +16 -0
  50. package/dist/common/tags.d.ts +4 -0
  51. package/dist/index.d.ts +11 -0
  52. package/package.json +5 -1
  53. package/src/control/common/api.ts +101 -11
  54. package/src/control/common/authoring.ts +7 -1
  55. package/src/control/common/authoringExamples.ts +9 -0
  56. package/src/control/common/authoringSchema.ts +18 -12
  57. package/src/control/common/errors.ts +6 -0
  58. package/src/control/common/flowDecoders.ts +1 -0
  59. package/src/control/common/mcp.ts +16 -0
  60. package/src/control/common/requests.ts +16 -2
  61. package/src/control/common/tags.ts +20 -0
  62. package/src/execution/common/events.ts +22 -7
  63. package/src/execution/common/node-execution.ts +3 -0
  64. package/src/execution/common/scheduler.ts +29 -13
  65. package/src/flow/common/change.ts +2 -1
  66. package/src/flow/common/changeSchema.ts +11 -1
  67. package/src/flow/common/errorHandling.ts +1 -1
  68. package/src/flow/common/semantics.ts +27 -1
  69. package/src/runtime/common/engineContract.ts +6 -3
  70. package/src/runtime/common/nodejsGuest.generated.json +11 -12
  71. package/src/runtime/common/runtime.ts +122 -7
  72. package/src/state/common/conformance.ts +81 -0
  73. package/src/state/common/state.ts +141 -0
  74. package/src/types/index.ts +11 -0
@@ -23,8 +23,8 @@ function dequal(foo, bar) {
23
23
  }
24
24
  //#endregion
25
25
  //#region src/runtime/common/engineContract.ts
26
- /** v9 is a single contract: the Node compatibility builtins, `context.fetch`, and no `context.egress`. */
27
- var currentEngineContract = "open-flow-engine/v9";
26
+ /** v10 adds persistent Flow State to the published v9 Node compatibility and fetch contract. */
27
+ var currentEngineContract = "open-flow-engine/v10";
28
28
  /** The published v8 Node compatibility contract, retained for existing Publications and Runs. */
29
29
  var nodejsEngineContract = "open-flow-engine/v8/nodejs-compat-v1";
30
30
  var platformSource = (contract) => `export const engineContract = ${JSON.stringify(contract)}
@@ -69,13 +69,19 @@ var nodejsContract = {
69
69
  ].flatMap((name) => [name, `node:${name}`])),
70
70
  platformSource: platformSource(nodejsEngineContract)
71
71
  };
72
- var currentContract = {
72
+ var v9Contract = {
73
73
  ...nodejsContract,
74
74
  codeFetch: true,
75
+ platformSource: platformSource("open-flow-engine/v9")
76
+ };
77
+ var currentContract = {
78
+ ...v9Contract,
79
+ flowState: true,
75
80
  platformSource: platformSource(currentEngineContract)
76
81
  };
77
82
  function findEngineContract(contract) {
78
- if (contract == "open-flow-engine/v9") return currentContract;
83
+ if (contract == "open-flow-engine/v10") return currentContract;
84
+ if (contract == "open-flow-engine/v9") return v9Contract;
79
85
  if (contract == "open-flow-engine/v8") return v8Contract;
80
86
  if (contract == "open-flow-engine/v8/nodejs-compat-v1") return nodejsContract;
81
87
  if (contract == "open-flow-engine/v7" || contract == "open-flow-engine/v7/nodejs-compat-v1") return {
@@ -95,6 +101,60 @@ function findEngineContract(contract) {
95
101
  }
96
102
  //#endregion
97
103
  //#region src/runtime/common/runtime.ts
104
+ /** Serialized into the guest; keep validation and helpers self-contained. */
105
+ function createState(invoke) {
106
+ const invalid = (message) => Object.assign(new TypeError(message), { code: "capability.invalid" });
107
+ const keyOf = (key) => {
108
+ if (typeof key !== "string" || key.length === 0 || new TextEncoder().encode(key).length > 256) throw invalid("State keys require 1 to 256 UTF-8 bytes.");
109
+ return key;
110
+ };
111
+ const valueOf = (value) => {
112
+ if (value === void 0) throw invalid("State values must be JSON.");
113
+ try {
114
+ return snapshotRuntimeResult({ value }).value;
115
+ } catch {
116
+ throw invalid("State values must be JSON.");
117
+ }
118
+ };
119
+ const idsOf = (ids) => {
120
+ if (!Array.isArray(ids) || !Array.from(ids).every((id) => typeof id === "string" || typeof id === "number" && Number.isFinite(id))) throw invalid("Identities must be strings or finite numbers.");
121
+ return ids;
122
+ };
123
+ return {
124
+ state: Object.freeze({
125
+ async get(key) {
126
+ return (await invoke("state.get", { key: keyOf(key) })).body.value;
127
+ },
128
+ async set(key, value) {
129
+ await invoke("state.set", {
130
+ key: keyOf(key),
131
+ value: valueOf(value)
132
+ });
133
+ },
134
+ async insert(key, value) {
135
+ if (value === null) throw invalid("State insert does not accept null.");
136
+ return (await invoke("state.insert", {
137
+ key: keyOf(key),
138
+ value: valueOf(value)
139
+ })).body.inserted;
140
+ },
141
+ async delete(key) {
142
+ await invoke("state.delete", { key: keyOf(key) });
143
+ },
144
+ async list() {
145
+ return (await invoke("state.list", {})).body.keys;
146
+ }
147
+ }),
148
+ dedupe: Object.freeze({
149
+ async insert(ids) {
150
+ return (await invoke("dedupe.insert", { ids: idsOf(ids) })).body.inserted;
151
+ },
152
+ async has(ids) {
153
+ return (await invoke("dedupe.has", { ids: idsOf(ids) })).body.present;
154
+ }
155
+ })
156
+ };
157
+ }
98
158
  /** Snapshot a Task result before JSON transport can discard or coerce invalid values. */
99
159
  function snapshotRuntimeResult(value) {
100
160
  const parents = /* @__PURE__ */ new Set();
@@ -394,6 +454,59 @@ async function rejects(operation, pattern, message) {
394
454
  throw new Error(`${message}: operation unexpectedly succeeded.`);
395
455
  }
396
456
  var runtimeConformanceCases = [
457
+ {
458
+ name: "cancels detached State work when its Task finishes",
459
+ async verify(harness) {
460
+ let aborted = false;
461
+ equal(await harness.invoke({
462
+ input: null,
463
+ invocationId: "state-detached",
464
+ capability: async ({ signal }) => await new Promise((resolve) => {
465
+ signal.addEventListener("abort", () => {
466
+ aborted = true;
467
+ resolve({
468
+ status: 200,
469
+ body: null
470
+ });
471
+ }, { once: true });
472
+ }),
473
+ program: program(harness, `export default async (_, context) => {
474
+ void context.state.set('detached', 1);
475
+ await new Promise(resolve => setTimeout(resolve, 20));
476
+ return null;
477
+ }`)
478
+ }), null, "Detached State Task result");
479
+ equal(aborted, true, "Detached State cancellation");
480
+ }
481
+ },
482
+ {
483
+ name: "rejects non-JSON State values and invalid identities before Host dispatch",
484
+ async verify(harness) {
485
+ let calls = 0;
486
+ equal(await harness.invoke({
487
+ input: null,
488
+ invocationId: "state-invalid",
489
+ capability: async () => {
490
+ calls += 1;
491
+ return {
492
+ status: 200,
493
+ body: null
494
+ };
495
+ },
496
+ program: program(harness, `export default async (_, context) => {
497
+ const cyclic = {}; cyclic.self = cyclic;
498
+ const invalid = [undefined, NaN, Infinity, new Date(), { x: undefined }, cyclic, [undefined], { x: () => 1 }];
499
+ const errors = [];
500
+ for (const value of invalid) { try { await context.state.set('key', value); errors.push('accepted'); } catch (e) { errors.push(e.code); } }
501
+ for (const call of [() => context.state.get(''), () => context.state.get('x'.repeat(257)), () => context.state.insert('x', null), () => context.dedupe.insert([NaN]), () => context.dedupe.has([null]), () => context.dedupe.insert(new Array(1))]) {
502
+ try { await call(); errors.push('accepted'); } catch (e) { errors.push(e.code); }
503
+ }
504
+ return errors;
505
+ }`)
506
+ }), Array.from({ length: 14 }, () => "capability.invalid"), "State boundary validation");
507
+ equal(calls, 0, "State invalid dispatch");
508
+ }
509
+ },
397
510
  {
398
511
  name: "rejects Task results that JSON transport would discard or coerce",
399
512
  async verify(harness) {
@@ -923,19 +1036,13 @@ function createBase64() {
923
1036
  const padding = text.endsWith("==") ? 2 : text.endsWith("=") ? 1 : 0;
924
1037
  const bytes = new Uint8Array(text.length / 4 * 3 - padding);
925
1038
  for (let index = 0, offset = 0; index < text.length; index += 4) {
926
- const digits = [
927
- 0,
928
- 1,
929
- 2,
930
- 3
931
- ].map((position) => {
1039
+ let value = 0;
1040
+ for (let position = 0; position < 4; position++) {
932
1041
  const code = text.charCodeAt(index + position);
933
- if (code == 61 && index + position >= text.length - padding) return 0;
934
- const value = code < 128 ? values[code] : 255;
935
- if (value == 255) throw new TypeError("Base64 content is invalid.");
936
- return value;
937
- });
938
- const value = digits[0] << 18 | digits[1] << 12 | digits[2] << 6 | digits[3];
1042
+ const digit = code == 61 && index + position >= text.length - padding ? 0 : code < 128 ? values[code] : 255;
1043
+ if (digit == 255) throw new TypeError("Base64 content is invalid.");
1044
+ value = value << 6 | digit;
1045
+ }
939
1046
  if (offset < bytes.length) bytes[offset++] = value >> 16;
940
1047
  if (offset < bytes.length) bytes[offset++] = value >> 8 & 255;
941
1048
  if (offset < bytes.length) bytes[offset++] = value & 255;
@@ -1098,4 +1205,4 @@ function createWorkflows(invoke) {
1098
1205
  } });
1099
1206
  }
1100
1207
  //#endregion
1101
- export { createActions, createArtifacts, createBase64, createFetch, createWorkflows, currentEngineContract, findEngineContract, nodejsEngineContract, nodejsRuntimeConformanceCases, resolveAction, runtimeConformanceCases, snapshotRuntimeResult };
1208
+ export { createActions, createArtifacts, createBase64, createFetch, createState, createWorkflows, currentEngineContract, findEngineContract, nodejsEngineContract, nodejsRuntimeConformanceCases, resolveAction, runtimeConformanceCases, snapshotRuntimeResult };