@synergenius/flow-weaver 0.8.3 → 0.9.1

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.
@@ -935,8 +935,8 @@ var require_command = __commonJS({
935
935
  "node_modules/commander/lib/command.js"(exports2) {
936
936
  var EventEmitter2 = __require("events").EventEmitter;
937
937
  var childProcess = __require("child_process");
938
- var path39 = __require("path");
939
- var fs38 = __require("fs");
938
+ var path42 = __require("path");
939
+ var fs41 = __require("fs");
940
940
  var process6 = __require("process");
941
941
  var { Argument: Argument2, humanReadableArgName } = require_argument();
942
942
  var { CommanderError: CommanderError2 } = require_error();
@@ -1759,10 +1759,10 @@ Expecting one of '${allowedValues.join("', '")}'`);
1759
1759
  let launchWithNode = false;
1760
1760
  const sourceExt = [".js", ".ts", ".tsx", ".mjs", ".cjs"];
1761
1761
  function findFile(baseDir, baseName) {
1762
- const localBin = path39.resolve(baseDir, baseName);
1763
- if (fs38.existsSync(localBin)) return localBin;
1764
- if (sourceExt.includes(path39.extname(baseName))) return void 0;
1765
- const foundExt = sourceExt.find((ext2) => fs38.existsSync(`${localBin}${ext2}`));
1762
+ const localBin = path42.resolve(baseDir, baseName);
1763
+ if (fs41.existsSync(localBin)) return localBin;
1764
+ if (sourceExt.includes(path42.extname(baseName))) return void 0;
1765
+ const foundExt = sourceExt.find((ext2) => fs41.existsSync(`${localBin}${ext2}`));
1766
1766
  if (foundExt) return `${localBin}${foundExt}`;
1767
1767
  return void 0;
1768
1768
  }
@@ -1773,23 +1773,23 @@ Expecting one of '${allowedValues.join("', '")}'`);
1773
1773
  if (this._scriptPath) {
1774
1774
  let resolvedScriptPath;
1775
1775
  try {
1776
- resolvedScriptPath = fs38.realpathSync(this._scriptPath);
1776
+ resolvedScriptPath = fs41.realpathSync(this._scriptPath);
1777
1777
  } catch (err) {
1778
1778
  resolvedScriptPath = this._scriptPath;
1779
1779
  }
1780
- executableDir = path39.resolve(path39.dirname(resolvedScriptPath), executableDir);
1780
+ executableDir = path42.resolve(path42.dirname(resolvedScriptPath), executableDir);
1781
1781
  }
1782
1782
  if (executableDir) {
1783
1783
  let localFile = findFile(executableDir, executableFile);
1784
1784
  if (!localFile && !subcommand._executableFile && this._scriptPath) {
1785
- const legacyName = path39.basename(this._scriptPath, path39.extname(this._scriptPath));
1785
+ const legacyName = path42.basename(this._scriptPath, path42.extname(this._scriptPath));
1786
1786
  if (legacyName !== this._name) {
1787
1787
  localFile = findFile(executableDir, `${legacyName}-${subcommand._name}`);
1788
1788
  }
1789
1789
  }
1790
1790
  executableFile = localFile || executableFile;
1791
1791
  }
1792
- launchWithNode = sourceExt.includes(path39.extname(executableFile));
1792
+ launchWithNode = sourceExt.includes(path42.extname(executableFile));
1793
1793
  let proc2;
1794
1794
  if (process6.platform !== "win32") {
1795
1795
  if (launchWithNode) {
@@ -2572,7 +2572,7 @@ Expecting one of '${allowedValues.join("', '")}'`);
2572
2572
  * @return {Command}
2573
2573
  */
2574
2574
  nameFromFilename(filename) {
2575
- this._name = path39.basename(filename, path39.extname(filename));
2575
+ this._name = path42.basename(filename, path42.extname(filename));
2576
2576
  return this;
2577
2577
  }
2578
2578
  /**
@@ -2586,9 +2586,9 @@ Expecting one of '${allowedValues.join("', '")}'`);
2586
2586
  * @param {string} [path]
2587
2587
  * @return {string|null|Command}
2588
2588
  */
2589
- executableDir(path40) {
2590
- if (path40 === void 0) return this._executableDir;
2591
- this._executableDir = path40;
2589
+ executableDir(path43) {
2590
+ if (path43 === void 0) return this._executableDir;
2591
+ this._executableDir = path43;
2592
2592
  return this;
2593
2593
  }
2594
2594
  /**
@@ -6458,10 +6458,10 @@ var init_esm3 = __esm({
6458
6458
  * Return a void Promise that resolves once the stream ends.
6459
6459
  */
6460
6460
  async promise() {
6461
- return new Promise((resolve28, reject2) => {
6461
+ return new Promise((resolve31, reject2) => {
6462
6462
  this.on(DESTROYED, () => reject2(new Error("stream destroyed")));
6463
6463
  this.on("error", (er) => reject2(er));
6464
- this.on("end", () => resolve28());
6464
+ this.on("end", () => resolve31());
6465
6465
  });
6466
6466
  }
6467
6467
  /**
@@ -6485,7 +6485,7 @@ var init_esm3 = __esm({
6485
6485
  return Promise.resolve({ done: false, value: res });
6486
6486
  if (this[EOF])
6487
6487
  return stop();
6488
- let resolve28;
6488
+ let resolve31;
6489
6489
  let reject2;
6490
6490
  const onerr = (er) => {
6491
6491
  this.off("data", ondata);
@@ -6499,19 +6499,19 @@ var init_esm3 = __esm({
6499
6499
  this.off("end", onend);
6500
6500
  this.off(DESTROYED, ondestroy);
6501
6501
  this.pause();
6502
- resolve28({ value: value2, done: !!this[EOF] });
6502
+ resolve31({ value: value2, done: !!this[EOF] });
6503
6503
  };
6504
6504
  const onend = () => {
6505
6505
  this.off("error", onerr);
6506
6506
  this.off("data", ondata);
6507
6507
  this.off(DESTROYED, ondestroy);
6508
6508
  stop();
6509
- resolve28({ done: true, value: void 0 });
6509
+ resolve31({ done: true, value: void 0 });
6510
6510
  };
6511
6511
  const ondestroy = () => onerr(new Error("stream destroyed"));
6512
6512
  return new Promise((res2, rej) => {
6513
6513
  reject2 = rej;
6514
- resolve28 = res2;
6514
+ resolve31 = res2;
6515
6515
  this.once(DESTROYED, ondestroy);
6516
6516
  this.once("error", onerr);
6517
6517
  this.once("end", onend);
@@ -6886,12 +6886,12 @@ var init_esm4 = __esm({
6886
6886
  /**
6887
6887
  * Get the Path object referenced by the string path, resolved from this Path
6888
6888
  */
6889
- resolve(path39) {
6890
- if (!path39) {
6889
+ resolve(path42) {
6890
+ if (!path42) {
6891
6891
  return this;
6892
6892
  }
6893
- const rootPath = this.getRootString(path39);
6894
- const dir = path39.substring(rootPath.length);
6893
+ const rootPath = this.getRootString(path42);
6894
+ const dir = path42.substring(rootPath.length);
6895
6895
  const dirParts = dir.split(this.splitSep);
6896
6896
  const result = rootPath ? this.getRoot(rootPath).#resolveParts(dirParts) : this.#resolveParts(dirParts);
6897
6897
  return result;
@@ -7495,9 +7495,9 @@ var init_esm4 = __esm({
7495
7495
  if (this.#asyncReaddirInFlight) {
7496
7496
  await this.#asyncReaddirInFlight;
7497
7497
  } else {
7498
- let resolve28 = () => {
7498
+ let resolve31 = () => {
7499
7499
  };
7500
- this.#asyncReaddirInFlight = new Promise((res) => resolve28 = res);
7500
+ this.#asyncReaddirInFlight = new Promise((res) => resolve31 = res);
7501
7501
  try {
7502
7502
  for (const e of await this.#fs.promises.readdir(fullpath, {
7503
7503
  withFileTypes: true
@@ -7510,7 +7510,7 @@ var init_esm4 = __esm({
7510
7510
  children.provisional = 0;
7511
7511
  }
7512
7512
  this.#asyncReaddirInFlight = void 0;
7513
- resolve28();
7513
+ resolve31();
7514
7514
  }
7515
7515
  return children.slice(0, children.provisional);
7516
7516
  }
@@ -7643,8 +7643,8 @@ var init_esm4 = __esm({
7643
7643
  /**
7644
7644
  * @internal
7645
7645
  */
7646
- getRootString(path39) {
7647
- return win32.parse(path39).root;
7646
+ getRootString(path42) {
7647
+ return win32.parse(path42).root;
7648
7648
  }
7649
7649
  /**
7650
7650
  * @internal
@@ -7690,8 +7690,8 @@ var init_esm4 = __esm({
7690
7690
  /**
7691
7691
  * @internal
7692
7692
  */
7693
- getRootString(path39) {
7694
- return path39.startsWith("/") ? "/" : "";
7693
+ getRootString(path42) {
7694
+ return path42.startsWith("/") ? "/" : "";
7695
7695
  }
7696
7696
  /**
7697
7697
  * @internal
@@ -7740,8 +7740,8 @@ var init_esm4 = __esm({
7740
7740
  *
7741
7741
  * @internal
7742
7742
  */
7743
- constructor(cwd = process.cwd(), pathImpl, sep2, { nocase, childrenCacheSize = 16 * 1024, fs: fs38 = defaultFS } = {}) {
7744
- this.#fs = fsFromOption(fs38);
7743
+ constructor(cwd = process.cwd(), pathImpl, sep2, { nocase, childrenCacheSize = 16 * 1024, fs: fs41 = defaultFS } = {}) {
7744
+ this.#fs = fsFromOption(fs41);
7745
7745
  if (cwd instanceof URL || cwd.startsWith("file://")) {
7746
7746
  cwd = fileURLToPath(cwd);
7747
7747
  }
@@ -7780,11 +7780,11 @@ var init_esm4 = __esm({
7780
7780
  /**
7781
7781
  * Get the depth of a provided path, string, or the cwd
7782
7782
  */
7783
- depth(path39 = this.cwd) {
7784
- if (typeof path39 === "string") {
7785
- path39 = this.cwd.resolve(path39);
7783
+ depth(path42 = this.cwd) {
7784
+ if (typeof path42 === "string") {
7785
+ path42 = this.cwd.resolve(path42);
7786
7786
  }
7787
- return path39.depth();
7787
+ return path42.depth();
7788
7788
  }
7789
7789
  /**
7790
7790
  * Return the cache of child entries. Exposed so subclasses can create
@@ -8271,9 +8271,9 @@ var init_esm4 = __esm({
8271
8271
  process6();
8272
8272
  return results;
8273
8273
  }
8274
- chdir(path39 = this.cwd) {
8274
+ chdir(path42 = this.cwd) {
8275
8275
  const oldCwd = this.cwd;
8276
- this.cwd = typeof path39 === "string" ? this.cwd.resolve(path39) : path39;
8276
+ this.cwd = typeof path42 === "string" ? this.cwd.resolve(path42) : path42;
8277
8277
  this.cwd[setAsCwd](oldCwd);
8278
8278
  }
8279
8279
  };
@@ -8299,8 +8299,8 @@ var init_esm4 = __esm({
8299
8299
  /**
8300
8300
  * @internal
8301
8301
  */
8302
- newRoot(fs38) {
8303
- return new PathWin32(this.rootPath, IFDIR, void 0, this.roots, this.nocase, this.childrenCache(), { fs: fs38 });
8302
+ newRoot(fs41) {
8303
+ return new PathWin32(this.rootPath, IFDIR, void 0, this.roots, this.nocase, this.childrenCache(), { fs: fs41 });
8304
8304
  }
8305
8305
  /**
8306
8306
  * Return true if the provided path string is an absolute path
@@ -8328,8 +8328,8 @@ var init_esm4 = __esm({
8328
8328
  /**
8329
8329
  * @internal
8330
8330
  */
8331
- newRoot(fs38) {
8332
- return new PathPosix(this.rootPath, IFDIR, void 0, this.roots, this.nocase, this.childrenCache(), { fs: fs38 });
8331
+ newRoot(fs41) {
8332
+ return new PathPosix(this.rootPath, IFDIR, void 0, this.roots, this.nocase, this.childrenCache(), { fs: fs41 });
8333
8333
  }
8334
8334
  /**
8335
8335
  * Return true if the provided path string is an absolute path
@@ -8648,8 +8648,8 @@ var init_processor = __esm({
8648
8648
  }
8649
8649
  // match, absolute, ifdir
8650
8650
  entries() {
8651
- return [...this.store.entries()].map(([path39, n]) => [
8652
- path39,
8651
+ return [...this.store.entries()].map(([path42, n]) => [
8652
+ path42,
8653
8653
  !!(n & 2),
8654
8654
  !!(n & 1)
8655
8655
  ]);
@@ -8862,9 +8862,9 @@ var init_walker = __esm({
8862
8862
  signal;
8863
8863
  maxDepth;
8864
8864
  includeChildMatches;
8865
- constructor(patterns, path39, opts) {
8865
+ constructor(patterns, path42, opts) {
8866
8866
  this.patterns = patterns;
8867
- this.path = path39;
8867
+ this.path = path42;
8868
8868
  this.opts = opts;
8869
8869
  this.#sep = !opts.posix && opts.platform === "win32" ? "\\" : "/";
8870
8870
  this.includeChildMatches = opts.includeChildMatches !== false;
@@ -8883,11 +8883,11 @@ var init_walker = __esm({
8883
8883
  });
8884
8884
  }
8885
8885
  }
8886
- #ignored(path39) {
8887
- return this.seen.has(path39) || !!this.#ignore?.ignored?.(path39);
8886
+ #ignored(path42) {
8887
+ return this.seen.has(path42) || !!this.#ignore?.ignored?.(path42);
8888
8888
  }
8889
- #childrenIgnored(path39) {
8890
- return !!this.#ignore?.childrenIgnored?.(path39);
8889
+ #childrenIgnored(path42) {
8890
+ return !!this.#ignore?.childrenIgnored?.(path42);
8891
8891
  }
8892
8892
  // backpressure mechanism
8893
8893
  pause() {
@@ -9102,8 +9102,8 @@ var init_walker = __esm({
9102
9102
  };
9103
9103
  GlobWalker = class extends GlobUtil {
9104
9104
  matches = /* @__PURE__ */ new Set();
9105
- constructor(patterns, path39, opts) {
9106
- super(patterns, path39, opts);
9105
+ constructor(patterns, path42, opts) {
9106
+ super(patterns, path42, opts);
9107
9107
  }
9108
9108
  matchEmit(e) {
9109
9109
  this.matches.add(e);
@@ -9140,8 +9140,8 @@ var init_walker = __esm({
9140
9140
  };
9141
9141
  GlobStream = class extends GlobUtil {
9142
9142
  results;
9143
- constructor(patterns, path39, opts) {
9144
- super(patterns, path39, opts);
9143
+ constructor(patterns, path42, opts) {
9144
+ super(patterns, path42, opts);
9145
9145
  this.results = new Minipass({
9146
9146
  signal: this.signal,
9147
9147
  objectMode: true
@@ -10352,17 +10352,17 @@ var require_binary_search = __commonJS({
10352
10352
  var require_read_wasm = __commonJS({
10353
10353
  "node_modules/source-map/lib/read-wasm.js"(exports2, module2) {
10354
10354
  "use strict";
10355
- var fs38 = __require("fs");
10356
- var path39 = __require("path");
10355
+ var fs41 = __require("fs");
10356
+ var path42 = __require("path");
10357
10357
  module2.exports = function readWasm() {
10358
- return new Promise((resolve28, reject2) => {
10359
- const wasmPath = path39.join(__dirname, "mappings.wasm");
10360
- fs38.readFile(wasmPath, null, (error2, data) => {
10358
+ return new Promise((resolve31, reject2) => {
10359
+ const wasmPath = path42.join(__dirname, "mappings.wasm");
10360
+ fs41.readFile(wasmPath, null, (error2, data) => {
10361
10361
  if (error2) {
10362
10362
  reject2(error2);
10363
10363
  return;
10364
10364
  }
10365
- resolve28(data.buffer);
10365
+ resolve31(data.buffer);
10366
10366
  });
10367
10367
  });
10368
10368
  };
@@ -11888,12 +11888,14 @@ var init_validator = __esm({
11888
11888
  MISSING_START_CONNECTION: `${DOCS_BASE}/concepts#start-and-exit`,
11889
11889
  MISSING_EXIT_CONNECTION: `${DOCS_BASE}/concepts#start-and-exit`,
11890
11890
  INFERRED_NODE_TYPE: `${DOCS_BASE}/node-conversion`,
11891
- DUPLICATE_CONNECTION: `${DOCS_BASE}/concepts#connections`
11891
+ DUPLICATE_CONNECTION: `${DOCS_BASE}/concepts#connections`,
11892
+ STUB_NODE: `${DOCS_BASE}/model-driven#stub-nodes`
11892
11893
  };
11893
11894
  WorkflowValidator = class {
11894
11895
  errors = [];
11895
11896
  warnings = [];
11896
11897
  strictMode = false;
11898
+ draftMode = false;
11897
11899
  /** Look up instance sourceLocation by instance ID */
11898
11900
  getInstanceLocation(workflow, instanceId) {
11899
11901
  const instance = workflow.instances.find((inst) => inst.id === instanceId);
@@ -11938,6 +11940,7 @@ var init_validator = __esm({
11938
11940
  this.errors = [];
11939
11941
  this.warnings = [];
11940
11942
  this.strictMode = options?.strictMode ?? false;
11943
+ this.draftMode = options?.mode === "draft";
11941
11944
  const nodeTypeMap = /* @__PURE__ */ new Map();
11942
11945
  workflow.nodeTypes.forEach((nodeType) => {
11943
11946
  nodeTypeMap.set(nodeType.functionName, nodeType);
@@ -11971,7 +11974,7 @@ var init_validator = __esm({
11971
11974
  });
11972
11975
  workflow.instances.forEach((instance) => {
11973
11976
  const nodeType = workflow.nodeTypes.find((nt) => nt.name === instance.nodeType || nt.functionName === instance.nodeType);
11974
- if (nodeType?.inferred) {
11977
+ if (nodeType?.inferred && nodeType.variant !== "STUB") {
11975
11978
  this.warnings.push({
11976
11979
  type: "warning",
11977
11980
  code: "INFERRED_NODE_TYPE",
@@ -11981,6 +11984,18 @@ var init_validator = __esm({
11981
11984
  });
11982
11985
  }
11983
11986
  });
11987
+ workflow.instances.forEach((instance) => {
11988
+ const nodeType = workflow.nodeTypes.find((nt) => nt.name === instance.nodeType || nt.functionName === instance.nodeType);
11989
+ if (nodeType?.variant === "STUB") {
11990
+ this.errors.push({
11991
+ type: "error",
11992
+ code: "STUB_NODE",
11993
+ message: `Node "${instance.id}" uses stub type "${instance.nodeType}" which has no implementation. Use draft mode to validate structure, or implement the node.`,
11994
+ node: instance.id,
11995
+ location: instance.sourceLocation
11996
+ });
11997
+ }
11998
+ });
11984
11999
  this.validateStructure(workflow);
11985
12000
  this.validateDuplicateNodeNames(workflow);
11986
12001
  this.validateMutableBindings(workflow);
@@ -12017,6 +12032,30 @@ var init_validator = __esm({
12017
12032
  return true;
12018
12033
  });
12019
12034
  }
12035
+ if (this.draftMode) {
12036
+ const stubTypeNames = new Set(
12037
+ workflow.nodeTypes.filter((nt) => nt.variant === "STUB").map((nt) => nt.functionName)
12038
+ );
12039
+ workflow.nodeTypes.filter((nt) => nt.variant === "STUB").forEach((nt) => {
12040
+ stubTypeNames.add(nt.name);
12041
+ });
12042
+ const stubInstanceIds = new Set(
12043
+ workflow.instances.filter((inst) => stubTypeNames.has(inst.nodeType)).map((inst) => inst.id)
12044
+ );
12045
+ const promoted = [];
12046
+ this.errors = this.errors.filter((err) => {
12047
+ if (err.code === "STUB_NODE") {
12048
+ promoted.push({ ...err, type: "warning" });
12049
+ return false;
12050
+ }
12051
+ if (err.code === "MISSING_REQUIRED_INPUT" && err.node && stubInstanceIds.has(err.node)) {
12052
+ promoted.push({ ...err, type: "warning" });
12053
+ return false;
12054
+ }
12055
+ return true;
12056
+ });
12057
+ this.warnings.push(...promoted);
12058
+ }
12020
12059
  for (const diag of [...this.errors, ...this.warnings]) {
12021
12060
  if (!diag.docUrl && ERROR_DOC_URLS[diag.code]) {
12022
12061
  diag.docUrl = ERROR_DOC_URLS[diag.code];
@@ -12589,13 +12628,13 @@ Add '@param ${fromPort}' to the workflow JSDoc and include it in the params obje
12589
12628
  connections.filter((c) => c.from.node === c.to.node).map((c) => c.from.node)
12590
12629
  );
12591
12630
  const nonSelfLoopConnections = connections.filter((c) => c.from.node !== c.to.node);
12592
- const dfs = (nodeName, path39) => {
12631
+ const dfs = (nodeName, path42) => {
12593
12632
  if (recursionStack.has(nodeName)) {
12594
12633
  if (selfLoopNodes.has(nodeName)) {
12595
12634
  return false;
12596
12635
  }
12597
- const cycleStart = path39.indexOf(nodeName);
12598
- const cyclePath = [...path39.slice(cycleStart), nodeName];
12636
+ const cycleStart = path42.indexOf(nodeName);
12637
+ const cyclePath = [...path42.slice(cycleStart), nodeName];
12599
12638
  const cycleNodes = cyclePath.slice(0, -1);
12600
12639
  const sortedCycle = [...cycleNodes].sort();
12601
12640
  const cycleKey = sortedCycle.join(",");
@@ -12617,7 +12656,7 @@ Add '@param ${fromPort}' to the workflow JSDoc and include it in the params obje
12617
12656
  return false;
12618
12657
  }
12619
12658
  recursionStack.add(nodeName);
12620
- const newPath = [...path39, nodeName];
12659
+ const newPath = [...path42, nodeName];
12621
12660
  const instance = instances.find((n) => n.id === nodeName);
12622
12661
  if (!instance) {
12623
12662
  recursionStack.delete(nodeName);
@@ -13288,9 +13327,9 @@ var validate_exports = {};
13288
13327
  __export(validate_exports, {
13289
13328
  validateWorkflow: () => validateWorkflow
13290
13329
  });
13291
- function validateWorkflow(ast, customRules) {
13292
- const result = validator.validate(ast);
13293
- const allRules = [...getAgentValidationRules(), ...customRules || []];
13330
+ function validateWorkflow(ast, options) {
13331
+ const result = validator.validate(ast, { mode: options?.mode });
13332
+ const allRules = [...getAgentValidationRules(), ...options?.customRules || []];
13294
13333
  for (const rule of allRules) {
13295
13334
  const ruleResults = rule.validate(ast);
13296
13335
  for (const err of ruleResults) {
@@ -13351,15 +13390,15 @@ async function loadAST(filePath) {
13351
13390
  async function saveASTAlongside(ast) {
13352
13391
  const sourceFile = ast.sourceFile;
13353
13392
  const dir = path6.dirname(sourceFile);
13354
- const basename17 = path6.basename(sourceFile, path6.extname(sourceFile));
13355
- const astFile = path6.join(dir, `${basename17}.ast.json`);
13393
+ const basename18 = path6.basename(sourceFile, path6.extname(sourceFile));
13394
+ const astFile = path6.join(dir, `${basename18}.ast.json`);
13356
13395
  await saveAST(ast, astFile);
13357
13396
  return astFile;
13358
13397
  }
13359
13398
  async function loadASTAlongside(sourceFile) {
13360
13399
  const dir = path6.dirname(sourceFile);
13361
- const basename17 = path6.basename(sourceFile, path6.extname(sourceFile));
13362
- const astFile = path6.join(dir, `${basename17}.ast.json`);
13400
+ const basename18 = path6.basename(sourceFile, path6.extname(sourceFile));
13401
+ const astFile = path6.join(dir, `${basename18}.ast.json`);
13363
13402
  return loadAST(astFile);
13364
13403
  }
13365
13404
  var init_serialization_node = __esm({
@@ -14827,15 +14866,15 @@ var require_route = __commonJS({
14827
14866
  };
14828
14867
  }
14829
14868
  function wrapConversion(toModel, graph) {
14830
- const path39 = [graph[toModel].parent, toModel];
14869
+ const path42 = [graph[toModel].parent, toModel];
14831
14870
  let fn = conversions[graph[toModel].parent][toModel];
14832
14871
  let cur = graph[toModel].parent;
14833
14872
  while (graph[cur].parent) {
14834
- path39.unshift(graph[cur].parent);
14873
+ path42.unshift(graph[cur].parent);
14835
14874
  fn = link(conversions[graph[cur].parent][cur], fn);
14836
14875
  cur = graph[cur].parent;
14837
14876
  }
14838
- fn.conversion = path39;
14877
+ fn.conversion = path42;
14839
14878
  return fn;
14840
14879
  }
14841
14880
  module2.exports = function(fromModel) {
@@ -15316,7 +15355,7 @@ var require_lib4 = __commonJS({
15316
15355
  // node_modules/xmlhttprequest-ssl/lib/XMLHttpRequest.js
15317
15356
  var require_XMLHttpRequest = __commonJS({
15318
15357
  "node_modules/xmlhttprequest-ssl/lib/XMLHttpRequest.js"(exports2, module2) {
15319
- var fs38 = __require("fs");
15358
+ var fs41 = __require("fs");
15320
15359
  var Url = __require("url");
15321
15360
  var spawn2 = __require("child_process").spawn;
15322
15361
  module2.exports = XMLHttpRequest3;
@@ -15474,7 +15513,7 @@ var require_XMLHttpRequest = __commonJS({
15474
15513
  throw new Error("XMLHttpRequest: Only GET method is supported");
15475
15514
  }
15476
15515
  if (settings.async) {
15477
- fs38.readFile(unescape(url2.pathname), function(error2, data2) {
15516
+ fs41.readFile(unescape(url2.pathname), function(error2, data2) {
15478
15517
  if (error2) {
15479
15518
  self2.handleError(error2, error2.errno || -1);
15480
15519
  } else {
@@ -15486,7 +15525,7 @@ var require_XMLHttpRequest = __commonJS({
15486
15525
  });
15487
15526
  } else {
15488
15527
  try {
15489
- this.response = fs38.readFileSync(unescape(url2.pathname));
15528
+ this.response = fs41.readFileSync(unescape(url2.pathname));
15490
15529
  this.responseText = this.response.toString("utf8");
15491
15530
  this.status = 200;
15492
15531
  setState(self2.DONE);
@@ -15612,15 +15651,15 @@ var require_XMLHttpRequest = __commonJS({
15612
15651
  } else {
15613
15652
  var contentFile = ".node-xmlhttprequest-content-" + process.pid;
15614
15653
  var syncFile = ".node-xmlhttprequest-sync-" + process.pid;
15615
- fs38.writeFileSync(syncFile, "", "utf8");
15654
+ fs41.writeFileSync(syncFile, "", "utf8");
15616
15655
  var execString = "var http = require('http'), https = require('https'), fs = require('fs');var doRequest = http" + (ssl ? "s" : "") + ".request;var options = " + JSON.stringify(options) + ";var responseText = '';var responseData = Buffer.alloc(0);var req = doRequest(options, function(response) {response.on('data', function(chunk) { var data = Buffer.from(chunk); responseText += data.toString('utf8'); responseData = Buffer.concat([responseData, data]);});response.on('end', function() {fs.writeFileSync('" + contentFile + "', JSON.stringify({err: null, data: {statusCode: response.statusCode, headers: response.headers, text: responseText, data: responseData.toString('base64')}}), 'utf8');fs.unlinkSync('" + syncFile + "');});response.on('error', function(error) {fs.writeFileSync('" + contentFile + "', 'NODE-XMLHTTPREQUEST-ERROR:' + JSON.stringify(error), 'utf8');fs.unlinkSync('" + syncFile + "');});}).on('error', function(error) {fs.writeFileSync('" + contentFile + "', 'NODE-XMLHTTPREQUEST-ERROR:' + JSON.stringify(error), 'utf8');fs.unlinkSync('" + syncFile + "');});" + (data ? "req.write('" + JSON.stringify(data).slice(1, -1).replace(/'/g, "\\'") + "');" : "") + "req.end();";
15617
15656
  var syncProc = spawn2(process.argv[0], ["-e", execString]);
15618
15657
  var statusText;
15619
- while (fs38.existsSync(syncFile)) {
15658
+ while (fs41.existsSync(syncFile)) {
15620
15659
  }
15621
- self2.responseText = fs38.readFileSync(contentFile, "utf8");
15660
+ self2.responseText = fs41.readFileSync(contentFile, "utf8");
15622
15661
  syncProc.stdin.end();
15623
- fs38.unlinkSync(contentFile);
15662
+ fs41.unlinkSync(contentFile);
15624
15663
  if (self2.responseText.match(/^NODE-XMLHTTPREQUEST-ERROR:/)) {
15625
15664
  var errorObj = JSON.parse(self2.responseText.replace(/^NODE-XMLHTTPREQUEST-ERROR:/, ""));
15626
15665
  self2.handleError(errorObj, 503);
@@ -23000,7 +23039,7 @@ var require_compile = __commonJS({
23000
23039
  const schOrFunc = root2.refs[ref];
23001
23040
  if (schOrFunc)
23002
23041
  return schOrFunc;
23003
- let _sch = resolve28.call(this, root2, ref);
23042
+ let _sch = resolve31.call(this, root2, ref);
23004
23043
  if (_sch === void 0) {
23005
23044
  const schema2 = (_a = root2.localRefs) === null || _a === void 0 ? void 0 : _a[ref];
23006
23045
  const { schemaId } = this.opts;
@@ -23027,7 +23066,7 @@ var require_compile = __commonJS({
23027
23066
  function sameSchemaEnv(s1, s2) {
23028
23067
  return s1.schema === s2.schema && s1.root === s2.root && s1.baseId === s2.baseId;
23029
23068
  }
23030
- function resolve28(root2, ref) {
23069
+ function resolve31(root2, ref) {
23031
23070
  let sch;
23032
23071
  while (typeof (sch = this.refs[ref]) == "string")
23033
23072
  ref = sch;
@@ -23242,8 +23281,8 @@ var require_utils = __commonJS({
23242
23281
  }
23243
23282
  return ind;
23244
23283
  }
23245
- function removeDotSegments(path39) {
23246
- let input = path39;
23284
+ function removeDotSegments(path42) {
23285
+ let input = path42;
23247
23286
  const output = [];
23248
23287
  let nextSlash = -1;
23249
23288
  let len = 0;
@@ -23442,8 +23481,8 @@ var require_schemes = __commonJS({
23442
23481
  wsComponent.secure = void 0;
23443
23482
  }
23444
23483
  if (wsComponent.resourceName) {
23445
- const [path39, query] = wsComponent.resourceName.split("?");
23446
- wsComponent.path = path39 && path39 !== "/" ? path39 : void 0;
23484
+ const [path42, query] = wsComponent.resourceName.split("?");
23485
+ wsComponent.path = path42 && path42 !== "/" ? path42 : void 0;
23447
23486
  wsComponent.query = query;
23448
23487
  wsComponent.resourceName = void 0;
23449
23488
  }
@@ -23602,7 +23641,7 @@ var require_fast_uri = __commonJS({
23602
23641
  }
23603
23642
  return uri;
23604
23643
  }
23605
- function resolve28(baseURI, relativeURI, options) {
23644
+ function resolve31(baseURI, relativeURI, options) {
23606
23645
  const schemelessOptions = options ? Object.assign({ scheme: "null" }, options) : { scheme: "null" };
23607
23646
  const resolved = resolveComponent(parse7(baseURI, schemelessOptions), parse7(relativeURI, schemelessOptions), schemelessOptions, true);
23608
23647
  schemelessOptions.skipEscape = true;
@@ -23829,7 +23868,7 @@ var require_fast_uri = __commonJS({
23829
23868
  var fastUri = {
23830
23869
  SCHEMES,
23831
23870
  normalize: normalize2,
23832
- resolve: resolve28,
23871
+ resolve: resolve31,
23833
23872
  resolveComponent,
23834
23873
  equal,
23835
23874
  serialize,
@@ -26805,12 +26844,12 @@ var require_dist = __commonJS({
26805
26844
  throw new Error(`Unknown format "${name}"`);
26806
26845
  return f;
26807
26846
  };
26808
- function addFormats(ajv, list, fs38, exportName) {
26847
+ function addFormats(ajv, list, fs41, exportName) {
26809
26848
  var _a;
26810
26849
  var _b;
26811
26850
  (_a = (_b = ajv.opts.code).formats) !== null && _a !== void 0 ? _a : _b.formats = (0, codegen_1._)`require("ajv-formats/dist/formats").${exportName}`;
26812
26851
  for (const f of list)
26813
- ajv.addFormat(f, fs38[f]);
26852
+ ajv.addFormat(f, fs41[f]);
26814
26853
  }
26815
26854
  module2.exports = exports2 = formatsPlugin;
26816
26855
  Object.defineProperty(exports2, "__esModule", { value: true });
@@ -29220,7 +29259,11 @@ function generateNodeCallWithContext(instance, nodeType, workflow, _availableVar
29220
29259
  });
29221
29260
  const resultVar = `${safeId}Result`;
29222
29261
  const awaitKeyword = nodeType.isAsync ? "await " : "";
29223
- if (nodeType.variant === "COERCION") {
29262
+ if (nodeType.variant === "STUB") {
29263
+ lines.push(
29264
+ `${indent} throw new Error('Node "${instanceId}" uses stub type "${functionName}" which has no implementation.');`
29265
+ );
29266
+ } else if (nodeType.variant === "COERCION") {
29224
29267
  const coerceExprMap = {
29225
29268
  __fw_toString: "String",
29226
29269
  __fw_toNumber: "Number",
@@ -30034,8 +30077,16 @@ function generateCode(ast, options) {
30034
30077
  moduleFormat = "esm",
30035
30078
  externalRuntimePath,
30036
30079
  constants = [],
30037
- externalNodeTypes = {}
30080
+ externalNodeTypes = {},
30081
+ generateStubs = false
30038
30082
  } = options || {};
30083
+ const stubNodeTypes = ast.nodeTypes.filter((nt) => nt.variant === "STUB");
30084
+ if (stubNodeTypes.length > 0 && !generateStubs) {
30085
+ const stubNames = stubNodeTypes.map((nt) => nt.functionName).join(", ");
30086
+ throw new Error(
30087
+ `Cannot generate code: workflow has ${stubNodeTypes.length} stub node(s) without implementation: ${stubNames}. Implement them or pass { generateStubs: true } to emit placeholder throws.`
30088
+ );
30089
+ }
30039
30090
  const { shouldBeAsync, warning } = validateWorkflowAsync(ast, ast.nodeTypes);
30040
30091
  if (warning && !production) {
30041
30092
  console.warn(warning);
@@ -30472,9 +30523,9 @@ function shouldUseStepTag(portName, port) {
30472
30523
 
30473
30524
  // src/sugar-optimizer.ts
30474
30525
  init_constants();
30475
- function validatePathMacro(path39, connections, instances) {
30526
+ function validatePathMacro(path42, connections, instances) {
30476
30527
  const instanceIds = new Set(instances.map((inst) => inst.id));
30477
- for (const step of path39.steps) {
30528
+ for (const step of path42.steps) {
30478
30529
  if (step.node === "Start" || step.node === "Exit") continue;
30479
30530
  if (!instanceIds.has(step.node)) return false;
30480
30531
  }
@@ -30484,9 +30535,9 @@ function validatePathMacro(path39, connections, instances) {
30484
30535
  connKeys.add(`${conn.from.node}.${conn.from.port}->${conn.to.node}.${conn.to.port}`);
30485
30536
  }
30486
30537
  }
30487
- for (let i = 0; i < path39.steps.length - 1; i++) {
30488
- const current2 = path39.steps[i];
30489
- const next = path39.steps[i + 1];
30538
+ for (let i = 0; i < path42.steps.length - 1; i++) {
30539
+ const current2 = path42.steps[i];
30540
+ const next = path42.steps[i + 1];
30490
30541
  const route = current2.route || "ok";
30491
30542
  let expectedKey;
30492
30543
  if (current2.node === "Start") {
@@ -30590,12 +30641,12 @@ function detectSugarPatterns(connections, instances, existingMacros, nodeTypes,
30590
30641
  }
30591
30642
  const candidateRoutes = [];
30592
30643
  const MAX_ROUTES = 20;
30593
- function dfs(node, path39, visited) {
30644
+ function dfs(node, path42, visited) {
30594
30645
  if (candidateRoutes.length >= MAX_ROUTES) return;
30595
30646
  if (node === "Exit") {
30596
- path39.push({ node: "Exit" });
30597
- candidateRoutes.push([...path39]);
30598
- path39.pop();
30647
+ path42.push({ node: "Exit" });
30648
+ candidateRoutes.push([...path42]);
30649
+ path42.pop();
30599
30650
  return;
30600
30651
  }
30601
30652
  if (visited.has(node)) return;
@@ -30607,15 +30658,15 @@ function detectSugarPatterns(connections, instances, existingMacros, nodeTypes,
30607
30658
  }
30608
30659
  if (edges.ok && !coveredByExistingMacro.has(edges.ok === "Exit" ? "" : edges.ok)) {
30609
30660
  const step = node === "Start" ? { node: "Start" } : { node };
30610
- path39.push(step);
30611
- dfs(edges.ok, path39, visited);
30612
- path39.pop();
30661
+ path42.push(step);
30662
+ dfs(edges.ok, path42, visited);
30663
+ path42.pop();
30613
30664
  }
30614
30665
  if (edges.fail && !coveredByExistingMacro.has(edges.fail === "Exit" ? "" : edges.fail)) {
30615
30666
  const step = { node, route: "fail" };
30616
- path39.push(step);
30617
- dfs(edges.fail, path39, visited);
30618
- path39.pop();
30667
+ path42.push(step);
30668
+ dfs(edges.fail, path42, visited);
30669
+ path42.pop();
30619
30670
  }
30620
30671
  visited.delete(node);
30621
30672
  }
@@ -30770,6 +30821,9 @@ var AnnotationGenerator = class {
30770
30821
  if (nodeType.variant === "COERCION") {
30771
30822
  return;
30772
30823
  }
30824
+ if (nodeType.variant === "STUB" && nodeType.inferred) {
30825
+ return;
30826
+ }
30773
30827
  lines.push(
30774
30828
  ...this.generateNodeTypeAnnotation(
30775
30829
  nodeType,
@@ -30799,7 +30853,12 @@ var AnnotationGenerator = class {
30799
30853
  }
30800
30854
  lines.push(` *`);
30801
30855
  }
30802
- lines.push(" * @flowWeaver nodeType");
30856
+ const isStub = nodeType.variant === "STUB";
30857
+ if (isStub || nodeType.expression) {
30858
+ lines.push(" * @flowWeaver node");
30859
+ } else {
30860
+ lines.push(" * @flowWeaver nodeType");
30861
+ }
30803
30862
  if (includeMetadata && nodeType.label) {
30804
30863
  lines.push(` * @label ${nodeType.label}`);
30805
30864
  }
@@ -30856,24 +30915,7 @@ var AnnotationGenerator = class {
30856
30915
  return `{ ${props.join(", ")} }`;
30857
30916
  }
30858
30917
  generateFunctionSignature(nodeType) {
30859
- const lines = [];
30860
- const params = ["execute: boolean"];
30861
- Object.entries(nodeType.inputs).forEach(([name, port]) => {
30862
- if (isExecutePort(name)) return;
30863
- const optional2 = port.optional ? "?" : "";
30864
- const defaultVal = port.default !== void 0 ? ` = ${JSON.stringify(port.default)}` : "";
30865
- params.push(`${name}${optional2}: ${this.mapDataTypeToTS(port.dataType)}${defaultVal}`);
30866
- });
30867
- const returns = ["onSuccess: boolean", "onFailure: boolean"];
30868
- Object.entries(nodeType.outputs).forEach(([name, port]) => {
30869
- if (isSuccessPort(name) || isFailurePort(name)) return;
30870
- returns.push(`${name}: ${this.mapDataTypeToTS(port.dataType)}`);
30871
- });
30872
- lines.push(`function ${nodeType.functionName}(${params.join(", ")}) {`);
30873
- lines.push(` if (!execute) return { onSuccess: false, onFailure: false };`);
30874
- lines.push(` return { onSuccess: true, onFailure: false };`);
30875
- lines.push(`}`);
30876
- return lines;
30918
+ return generateFunctionSignature(nodeType);
30877
30919
  }
30878
30920
  generateWorkflowAnnotation(workflow, indent, includeComments, skipParamReturns = false) {
30879
30921
  const lines = [];
@@ -31030,6 +31072,10 @@ var AnnotationGenerator = class {
31030
31072
  }
31031
31073
  generateWorkflowFunctionSignature(workflow) {
31032
31074
  const lines = [];
31075
+ if (workflow.stub) {
31076
+ lines.push(`export const ${workflow.functionName} = 'flowWeaver:draft';`);
31077
+ return lines;
31078
+ }
31033
31079
  const startPorts = workflow.startPorts || {};
31034
31080
  const exitPorts = workflow.exitPorts || {};
31035
31081
  const params = [];
@@ -31213,6 +31259,51 @@ function generateNodeInstanceTag(instance) {
31213
31259
  }
31214
31260
  return ` * @node ${instance.id} ${instance.nodeType}${parent}${labelAttr}${portOrderAttr}${portLabelAttr}${exprAttr}${pullExecutionAttr}${minimizedAttr}${colorAttr}${iconAttr}${tagsAttr}${sizeAttr}${positionAttr}`;
31215
31261
  }
31262
+ function generateFunctionSignature(nodeType) {
31263
+ const lines = [];
31264
+ const isStub = nodeType.variant === "STUB";
31265
+ const isExpression = isStub || nodeType.expression;
31266
+ if (isExpression) {
31267
+ const params = [];
31268
+ Object.entries(nodeType.inputs).forEach(([name, port]) => {
31269
+ if (isExecutePort(name)) return;
31270
+ const optional2 = port.optional ? "?" : "";
31271
+ params.push(`${name}${optional2}: ${mapToTypeScript(port.dataType)}`);
31272
+ });
31273
+ const returns = [];
31274
+ Object.entries(nodeType.outputs).forEach(([name, port]) => {
31275
+ if (isSuccessPort(name) || isFailurePort(name)) return;
31276
+ returns.push(`${name}: ${mapToTypeScript(port.dataType)}`);
31277
+ });
31278
+ const returnType = returns.length === 1 ? mapToTypeScript(Object.entries(nodeType.outputs).find(([n]) => !isSuccessPort(n) && !isFailurePort(n))?.[1].dataType || "ANY") : `{ ${returns.join("; ")} }`;
31279
+ if (isStub) {
31280
+ lines.push(`declare function ${nodeType.functionName}(${params.join(", ")}): ${returnType};`);
31281
+ } else {
31282
+ lines.push(`function ${nodeType.functionName}(${params.join(", ")}): ${returnType} {`);
31283
+ lines.push(` // TODO: implement`);
31284
+ lines.push(` throw new Error('Not implemented');`);
31285
+ lines.push(`}`);
31286
+ }
31287
+ } else {
31288
+ const params = ["execute: boolean"];
31289
+ Object.entries(nodeType.inputs).forEach(([name, port]) => {
31290
+ if (isExecutePort(name)) return;
31291
+ const optional2 = port.optional ? "?" : "";
31292
+ const defaultVal = port.default !== void 0 ? ` = ${JSON.stringify(port.default)}` : "";
31293
+ params.push(`${name}${optional2}: ${mapToTypeScript(port.dataType)}${defaultVal}`);
31294
+ });
31295
+ const returns = ["onSuccess: boolean", "onFailure: boolean"];
31296
+ Object.entries(nodeType.outputs).forEach(([name, port]) => {
31297
+ if (isSuccessPort(name) || isFailurePort(name)) return;
31298
+ returns.push(`${name}: ${mapToTypeScript(port.dataType)}`);
31299
+ });
31300
+ lines.push(`function ${nodeType.functionName}(${params.join(", ")}) {`);
31301
+ lines.push(` if (!execute) return { onSuccess: false, onFailure: false };`);
31302
+ lines.push(` return { onSuccess: true, onFailure: false };`);
31303
+ lines.push(`}`);
31304
+ }
31305
+ return lines;
31306
+ }
31216
31307
  var annotationGenerator = new AnnotationGenerator();
31217
31308
 
31218
31309
  // src/api/generate-in-place.ts
@@ -33444,19 +33535,19 @@ function toKey(value2) {
33444
33535
  var toKey_default = toKey;
33445
33536
 
33446
33537
  // node_modules/lodash-es/_baseGet.js
33447
- function baseGet(object3, path39) {
33448
- path39 = castPath_default(path39, object3);
33449
- var index = 0, length = path39.length;
33538
+ function baseGet(object3, path42) {
33539
+ path42 = castPath_default(path42, object3);
33540
+ var index = 0, length = path42.length;
33450
33541
  while (object3 != null && index < length) {
33451
- object3 = object3[toKey_default(path39[index++])];
33542
+ object3 = object3[toKey_default(path42[index++])];
33452
33543
  }
33453
33544
  return index && index == length ? object3 : void 0;
33454
33545
  }
33455
33546
  var baseGet_default = baseGet;
33456
33547
 
33457
33548
  // node_modules/lodash-es/get.js
33458
- function get(object3, path39, defaultValue) {
33459
- var result = object3 == null ? void 0 : baseGet_default(object3, path39);
33549
+ function get(object3, path42, defaultValue) {
33550
+ var result = object3 == null ? void 0 : baseGet_default(object3, path42);
33460
33551
  return result === void 0 ? defaultValue : result;
33461
33552
  }
33462
33553
  var get_default = get;
@@ -34368,11 +34459,11 @@ function baseHasIn(object3, key) {
34368
34459
  var baseHasIn_default = baseHasIn;
34369
34460
 
34370
34461
  // node_modules/lodash-es/_hasPath.js
34371
- function hasPath(object3, path39, hasFunc) {
34372
- path39 = castPath_default(path39, object3);
34373
- var index = -1, length = path39.length, result = false;
34462
+ function hasPath(object3, path42, hasFunc) {
34463
+ path42 = castPath_default(path42, object3);
34464
+ var index = -1, length = path42.length, result = false;
34374
34465
  while (++index < length) {
34375
- var key = toKey_default(path39[index]);
34466
+ var key = toKey_default(path42[index]);
34376
34467
  if (!(result = object3 != null && hasFunc(object3, key))) {
34377
34468
  break;
34378
34469
  }
@@ -34387,21 +34478,21 @@ function hasPath(object3, path39, hasFunc) {
34387
34478
  var hasPath_default = hasPath;
34388
34479
 
34389
34480
  // node_modules/lodash-es/hasIn.js
34390
- function hasIn(object3, path39) {
34391
- return object3 != null && hasPath_default(object3, path39, baseHasIn_default);
34481
+ function hasIn(object3, path42) {
34482
+ return object3 != null && hasPath_default(object3, path42, baseHasIn_default);
34392
34483
  }
34393
34484
  var hasIn_default = hasIn;
34394
34485
 
34395
34486
  // node_modules/lodash-es/_baseMatchesProperty.js
34396
34487
  var COMPARE_PARTIAL_FLAG6 = 1;
34397
34488
  var COMPARE_UNORDERED_FLAG4 = 2;
34398
- function baseMatchesProperty(path39, srcValue) {
34399
- if (isKey_default(path39) && isStrictComparable_default(srcValue)) {
34400
- return matchesStrictComparable_default(toKey_default(path39), srcValue);
34489
+ function baseMatchesProperty(path42, srcValue) {
34490
+ if (isKey_default(path42) && isStrictComparable_default(srcValue)) {
34491
+ return matchesStrictComparable_default(toKey_default(path42), srcValue);
34401
34492
  }
34402
34493
  return function(object3) {
34403
- var objValue = get_default(object3, path39);
34404
- return objValue === void 0 && objValue === srcValue ? hasIn_default(object3, path39) : baseIsEqual_default(srcValue, objValue, COMPARE_PARTIAL_FLAG6 | COMPARE_UNORDERED_FLAG4);
34494
+ var objValue = get_default(object3, path42);
34495
+ return objValue === void 0 && objValue === srcValue ? hasIn_default(object3, path42) : baseIsEqual_default(srcValue, objValue, COMPARE_PARTIAL_FLAG6 | COMPARE_UNORDERED_FLAG4);
34405
34496
  };
34406
34497
  }
34407
34498
  var baseMatchesProperty_default = baseMatchesProperty;
@@ -34415,16 +34506,16 @@ function baseProperty(key) {
34415
34506
  var baseProperty_default = baseProperty;
34416
34507
 
34417
34508
  // node_modules/lodash-es/_basePropertyDeep.js
34418
- function basePropertyDeep(path39) {
34509
+ function basePropertyDeep(path42) {
34419
34510
  return function(object3) {
34420
- return baseGet_default(object3, path39);
34511
+ return baseGet_default(object3, path42);
34421
34512
  };
34422
34513
  }
34423
34514
  var basePropertyDeep_default = basePropertyDeep;
34424
34515
 
34425
34516
  // node_modules/lodash-es/property.js
34426
- function property(path39) {
34427
- return isKey_default(path39) ? baseProperty_default(toKey_default(path39)) : basePropertyDeep_default(path39);
34517
+ function property(path42) {
34518
+ return isKey_default(path42) ? baseProperty_default(toKey_default(path42)) : basePropertyDeep_default(path42);
34428
34519
  }
34429
34520
  var property_default = property;
34430
34521
 
@@ -34792,8 +34883,8 @@ function baseHas(object3, key) {
34792
34883
  var baseHas_default = baseHas;
34793
34884
 
34794
34885
  // node_modules/lodash-es/has.js
34795
- function has(object3, path39) {
34796
- return object3 != null && hasPath_default(object3, path39, baseHas_default);
34886
+ function has(object3, path42) {
34887
+ return object3 != null && hasPath_default(object3, path42, baseHas_default);
34797
34888
  }
34798
34889
  var has_default = has;
34799
34890
 
@@ -34916,14 +35007,14 @@ function negate(predicate) {
34916
35007
  var negate_default = negate;
34917
35008
 
34918
35009
  // node_modules/lodash-es/_baseSet.js
34919
- function baseSet(object3, path39, value2, customizer) {
35010
+ function baseSet(object3, path42, value2, customizer) {
34920
35011
  if (!isObject_default(object3)) {
34921
35012
  return object3;
34922
35013
  }
34923
- path39 = castPath_default(path39, object3);
34924
- var index = -1, length = path39.length, lastIndex = length - 1, nested = object3;
35014
+ path42 = castPath_default(path42, object3);
35015
+ var index = -1, length = path42.length, lastIndex = length - 1, nested = object3;
34925
35016
  while (nested != null && ++index < length) {
34926
- var key = toKey_default(path39[index]), newValue = value2;
35017
+ var key = toKey_default(path42[index]), newValue = value2;
34927
35018
  if (key === "__proto__" || key === "constructor" || key === "prototype") {
34928
35019
  return object3;
34929
35020
  }
@@ -34931,7 +35022,7 @@ function baseSet(object3, path39, value2, customizer) {
34931
35022
  var objValue = nested[key];
34932
35023
  newValue = customizer ? customizer(objValue, key, nested) : void 0;
34933
35024
  if (newValue === void 0) {
34934
- newValue = isObject_default(objValue) ? objValue : isIndex_default(path39[index + 1]) ? [] : {};
35025
+ newValue = isObject_default(objValue) ? objValue : isIndex_default(path42[index + 1]) ? [] : {};
34935
35026
  }
34936
35027
  }
34937
35028
  assignValue_default(nested, key, newValue);
@@ -34945,9 +35036,9 @@ var baseSet_default = baseSet;
34945
35036
  function basePickBy(object3, paths, predicate) {
34946
35037
  var index = -1, length = paths.length, result = {};
34947
35038
  while (++index < length) {
34948
- var path39 = paths[index], value2 = baseGet_default(object3, path39);
34949
- if (predicate(value2, path39)) {
34950
- baseSet_default(result, castPath_default(path39, object3), value2);
35039
+ var path42 = paths[index], value2 = baseGet_default(object3, path42);
35040
+ if (predicate(value2, path42)) {
35041
+ baseSet_default(result, castPath_default(path42, object3), value2);
34951
35042
  }
34952
35043
  }
34953
35044
  return result;
@@ -34963,8 +35054,8 @@ function pickBy(object3, predicate) {
34963
35054
  return [prop];
34964
35055
  });
34965
35056
  predicate = baseIteratee_default(predicate);
34966
- return basePickBy_default(object3, props, function(value2, path39) {
34967
- return predicate(value2, path39[0]);
35057
+ return basePickBy_default(object3, props, function(value2, path42) {
35058
+ return predicate(value2, path42[0]);
34968
35059
  });
34969
35060
  }
34970
35061
  var pickBy_default = pickBy;
@@ -37463,12 +37554,12 @@ function assignCategoriesMapProp(tokenTypes) {
37463
37554
  singleAssignCategoriesToksMap([], currTokType);
37464
37555
  });
37465
37556
  }
37466
- function singleAssignCategoriesToksMap(path39, nextNode) {
37467
- forEach_default(path39, (pathNode) => {
37557
+ function singleAssignCategoriesToksMap(path42, nextNode) {
37558
+ forEach_default(path42, (pathNode) => {
37468
37559
  nextNode.categoryMatchesMap[pathNode.tokenTypeIdx] = true;
37469
37560
  });
37470
37561
  forEach_default(nextNode.CATEGORIES, (nextCategory) => {
37471
- const newPath = path39.concat(nextNode);
37562
+ const newPath = path42.concat(nextNode);
37472
37563
  if (!includes_default(newPath, nextCategory)) {
37473
37564
  singleAssignCategoriesToksMap(newPath, nextCategory);
37474
37565
  }
@@ -38312,10 +38403,10 @@ var GastRefResolverVisitor = class extends GAstVisitor {
38312
38403
 
38313
38404
  // node_modules/chevrotain/lib/src/parse/grammar/interpreter.js
38314
38405
  var AbstractNextPossibleTokensWalker = class extends RestWalker {
38315
- constructor(topProd, path39) {
38406
+ constructor(topProd, path42) {
38316
38407
  super();
38317
38408
  this.topProd = topProd;
38318
- this.path = path39;
38409
+ this.path = path42;
38319
38410
  this.possibleTokTypes = [];
38320
38411
  this.nextProductionName = "";
38321
38412
  this.nextProductionOccurrence = 0;
@@ -38359,9 +38450,9 @@ var AbstractNextPossibleTokensWalker = class extends RestWalker {
38359
38450
  }
38360
38451
  };
38361
38452
  var NextAfterTokenWalker = class extends AbstractNextPossibleTokensWalker {
38362
- constructor(topProd, path39) {
38363
- super(topProd, path39);
38364
- this.path = path39;
38453
+ constructor(topProd, path42) {
38454
+ super(topProd, path42);
38455
+ this.path = path42;
38365
38456
  this.nextTerminalName = "";
38366
38457
  this.nextTerminalOccurrence = 0;
38367
38458
  this.nextTerminalName = this.path.lastTok.name;
@@ -38957,10 +39048,10 @@ function initializeArrayOfArrays(size) {
38957
39048
  }
38958
39049
  return result;
38959
39050
  }
38960
- function pathToHashKeys(path39) {
39051
+ function pathToHashKeys(path42) {
38961
39052
  let keys2 = [""];
38962
- for (let i = 0; i < path39.length; i++) {
38963
- const tokType = path39[i];
39053
+ for (let i = 0; i < path42.length; i++) {
39054
+ const tokType = path42[i];
38964
39055
  const longerKeys = [];
38965
39056
  for (let j = 0; j < keys2.length; j++) {
38966
39057
  const currShorterKey = keys2[j];
@@ -39199,7 +39290,7 @@ function validateRuleIsOverridden(ruleName, definedRulesNames, className) {
39199
39290
  }
39200
39291
  return errors2;
39201
39292
  }
39202
- function validateNoLeftRecursion(topRule, currRule, errMsgProvider, path39 = []) {
39293
+ function validateNoLeftRecursion(topRule, currRule, errMsgProvider, path42 = []) {
39203
39294
  const errors2 = [];
39204
39295
  const nextNonTerminals = getFirstNoneTerminal(currRule.definition);
39205
39296
  if (isEmpty_default(nextNonTerminals)) {
@@ -39211,15 +39302,15 @@ function validateNoLeftRecursion(topRule, currRule, errMsgProvider, path39 = [])
39211
39302
  errors2.push({
39212
39303
  message: errMsgProvider.buildLeftRecursionError({
39213
39304
  topLevelRule: topRule,
39214
- leftRecursionPath: path39
39305
+ leftRecursionPath: path42
39215
39306
  }),
39216
39307
  type: ParserDefinitionErrorType.LEFT_RECURSION,
39217
39308
  ruleName
39218
39309
  });
39219
39310
  }
39220
- const validNextSteps = difference_default(nextNonTerminals, path39.concat([topRule]));
39311
+ const validNextSteps = difference_default(nextNonTerminals, path42.concat([topRule]));
39221
39312
  const errorsFromNextSteps = flatMap_default(validNextSteps, (currRefRule) => {
39222
- const newPath = clone_default(path39);
39313
+ const newPath = clone_default(path42);
39223
39314
  newPath.push(currRefRule);
39224
39315
  return validateNoLeftRecursion(topRule, currRefRule, errMsgProvider, newPath);
39225
39316
  });
@@ -44734,38 +44825,39 @@ function assignImplicitPortOrders(ports) {
44734
44825
  scopeGroups.get(scopeKey).push([portName, portDef]);
44735
44826
  }
44736
44827
  for (const [scope, portsInScope] of scopeGroups.entries()) {
44828
+ let nextSlot2 = function(from) {
44829
+ while (occupied.has(from)) from++;
44830
+ occupied.add(from);
44831
+ return from;
44832
+ };
44833
+ var nextSlot = nextSlot2;
44737
44834
  const isScoped = scope !== void 0;
44738
- const mandatoryPorts = portsInScope.filter(([name]) => isMandatoryPort(name, isScoped));
44739
- const regularPorts = portsInScope.filter(([name]) => !isMandatoryPort(name, isScoped));
44740
- let minRegularExplicitOrder = Infinity;
44741
- for (const [, portDef] of regularPorts) {
44835
+ const occupied = /* @__PURE__ */ new Set();
44836
+ for (const [, portDef] of portsInScope) {
44742
44837
  const order = portDef.metadata?.order;
44743
44838
  if (typeof order === "number") {
44744
- minRegularExplicitOrder = Math.min(minRegularExplicitOrder, order);
44839
+ occupied.add(order);
44745
44840
  }
44746
44841
  }
44747
- let mandatoryStartOrder = 0;
44748
- if (minRegularExplicitOrder !== Infinity && minRegularExplicitOrder === 0) {
44749
- const regularPortsWithOrder0 = regularPorts.filter(([, p]) => p.metadata?.order === 0);
44750
- mandatoryStartOrder = regularPortsWithOrder0.length;
44751
- }
44752
- let currentMandatoryOrder = mandatoryStartOrder;
44753
- for (const [, portDef] of mandatoryPorts) {
44754
- if (portDef.metadata?.order === void 0) {
44755
- if (!portDef.metadata) {
44756
- portDef.metadata = {};
44757
- }
44758
- portDef.metadata.order = currentMandatoryOrder++;
44759
- }
44842
+ const mandatoryNeedOrder = portsInScope.filter(
44843
+ ([name, def]) => isMandatoryPort(name, isScoped) && def.metadata?.order === void 0
44844
+ );
44845
+ const regularNeedOrder = portsInScope.filter(
44846
+ ([name, def]) => !isMandatoryPort(name, isScoped) && def.metadata?.order === void 0
44847
+ );
44848
+ let slot = -mandatoryNeedOrder.length;
44849
+ for (const [, portDef] of mandatoryNeedOrder) {
44850
+ if (!portDef.metadata) portDef.metadata = {};
44851
+ slot = nextSlot2(slot);
44852
+ portDef.metadata.order = slot;
44853
+ slot++;
44760
44854
  }
44761
- let currentRegularOrder = currentMandatoryOrder;
44762
- for (const [, portDef] of regularPorts) {
44763
- if (portDef.metadata?.order === void 0) {
44764
- if (!portDef.metadata) {
44765
- portDef.metadata = {};
44766
- }
44767
- portDef.metadata.order = currentRegularOrder++;
44768
- }
44855
+ slot = Math.max(slot, 0);
44856
+ for (const [, portDef] of regularNeedOrder) {
44857
+ if (!portDef.metadata) portDef.metadata = {};
44858
+ slot = nextSlot2(slot);
44859
+ portDef.metadata.order = slot;
44860
+ slot++;
44769
44861
  }
44770
44862
  }
44771
44863
  }
@@ -47065,8 +47157,8 @@ ${errorMessages.join("\n")}`);
47065
47157
  }
47066
47158
  function getDefaultOutputFile(sourceFile) {
47067
47159
  const dir = path7.dirname(sourceFile);
47068
- const basename17 = path7.basename(sourceFile, ".ts");
47069
- return path7.join(dir, `${basename17}.generated.ts`);
47160
+ const basename18 = path7.basename(sourceFile, ".ts");
47161
+ return path7.join(dir, `${basename18}.generated.ts`);
47070
47162
  }
47071
47163
 
47072
47164
  // src/api/index.ts
@@ -47341,7 +47433,7 @@ function processResult(result, scope) {
47341
47433
  }
47342
47434
  return result !== NOTHING ? result : void 0;
47343
47435
  }
47344
- function finalize(rootScope, value2, path39) {
47436
+ function finalize(rootScope, value2, path42) {
47345
47437
  if (isFrozen(value2))
47346
47438
  return value2;
47347
47439
  const useStrictIteration = rootScope.immer_.shouldUseStrictIteration();
@@ -47349,7 +47441,7 @@ function finalize(rootScope, value2, path39) {
47349
47441
  if (!state) {
47350
47442
  each(
47351
47443
  value2,
47352
- (key, childValue) => finalizeProperty(rootScope, state, value2, key, childValue, path39),
47444
+ (key, childValue) => finalizeProperty(rootScope, state, value2, key, childValue, path42),
47353
47445
  useStrictIteration
47354
47446
  );
47355
47447
  return value2;
@@ -47379,16 +47471,16 @@ function finalize(rootScope, value2, path39) {
47379
47471
  result,
47380
47472
  key,
47381
47473
  childValue,
47382
- path39,
47474
+ path42,
47383
47475
  isSet22
47384
47476
  ),
47385
47477
  useStrictIteration
47386
47478
  );
47387
47479
  maybeFreeze(rootScope, result, false);
47388
- if (path39 && rootScope.patches_) {
47480
+ if (path42 && rootScope.patches_) {
47389
47481
  getPlugin("Patches").generatePatches_(
47390
47482
  state,
47391
- path39,
47483
+ path42,
47392
47484
  rootScope.patches_,
47393
47485
  rootScope.inversePatches_
47394
47486
  );
@@ -47410,9 +47502,9 @@ function finalizeProperty(rootScope, parentState, targetObject, prop, childValue
47410
47502
  if (process.env.NODE_ENV !== "production" && childValue === targetObject)
47411
47503
  die(5);
47412
47504
  if (isDraft(childValue)) {
47413
- const path39 = rootPath && parentState && parentState.type_ !== 3 && // Set objects are atomic since they have no keys.
47505
+ const path42 = rootPath && parentState && parentState.type_ !== 3 && // Set objects are atomic since they have no keys.
47414
47506
  !has2(parentState.assigned_, prop) ? rootPath.concat(prop) : void 0;
47415
- const res = finalize(rootScope, childValue, path39);
47507
+ const res = finalize(rootScope, childValue, path42);
47416
47508
  set(targetObject, prop, res);
47417
47509
  if (isDraft(res)) {
47418
47510
  rootScope.canAutoFreeze_ = false;
@@ -58273,17 +58365,17 @@ function buildAdjacency(ast) {
58273
58365
  function enumeratePaths(ast) {
58274
58366
  const { fromStart, toExit, edges } = buildAdjacency(ast);
58275
58367
  const paths = [];
58276
- function dfs(current2, path39, visited) {
58368
+ function dfs(current2, path42, visited) {
58277
58369
  if (toExit.has(current2)) {
58278
- paths.push([...path39, "Exit"]);
58370
+ paths.push([...path42, "Exit"]);
58279
58371
  }
58280
58372
  const targets = edges.get(current2) || [];
58281
58373
  for (const next of targets) {
58282
58374
  if (!visited.has(next)) {
58283
58375
  visited.add(next);
58284
- path39.push(next);
58285
- dfs(next, path39, visited);
58286
- path39.pop();
58376
+ path42.push(next);
58377
+ dfs(next, path42, visited);
58378
+ path42.pop();
58287
58379
  visited.delete(next);
58288
58380
  }
58289
58381
  }
@@ -58297,22 +58389,22 @@ function enumeratePaths(ast) {
58297
58389
  function buildGraph(ast) {
58298
58390
  const { fromStart, toExit, edges } = buildAdjacency(ast);
58299
58391
  const lines = [];
58300
- function dfs(current2, path39, visited) {
58392
+ function dfs(current2, path42, visited) {
58301
58393
  if (toExit.has(current2)) {
58302
- lines.push([...path39, "Exit"].join(" -> "));
58394
+ lines.push([...path42, "Exit"].join(" -> "));
58303
58395
  }
58304
58396
  const targets = edges.get(current2) || [];
58305
58397
  for (const next of targets) {
58306
58398
  if (!visited.has(next)) {
58307
58399
  visited.add(next);
58308
- path39.push(next);
58309
- dfs(next, path39, visited);
58310
- path39.pop();
58400
+ path42.push(next);
58401
+ dfs(next, path42, visited);
58402
+ path42.pop();
58311
58403
  visited.delete(next);
58312
58404
  }
58313
58405
  }
58314
58406
  if (targets.length === 0 && !toExit.has(current2)) {
58315
- lines.push(path39.join(" -> "));
58407
+ lines.push(path42.join(" -> "));
58316
58408
  }
58317
58409
  }
58318
58410
  fromStart.forEach((startNode) => {
@@ -59223,14 +59315,14 @@ function waypointsToSvgPath(waypoints, cornerRadius) {
59223
59315
  radii[i + 1] *= scale;
59224
59316
  }
59225
59317
  }
59226
- let path39 = `M ${waypoints[0][0]},${waypoints[0][1]}`;
59318
+ let path42 = `M ${waypoints[0][0]},${waypoints[0][1]}`;
59227
59319
  for (let i = 1; i < waypoints.length - 1; i++) {
59228
59320
  const prev = waypoints[i - 1];
59229
59321
  const curr = waypoints[i];
59230
59322
  const next = waypoints[i + 1];
59231
59323
  const r = radii[i];
59232
59324
  if (r < 2) {
59233
- path39 += ` L ${curr[0]},${curr[1]}`;
59325
+ path42 += ` L ${curr[0]},${curr[1]}`;
59234
59326
  continue;
59235
59327
  }
59236
59328
  const dPrev = [prev[0] - curr[0], prev[1] - curr[1]];
@@ -59243,12 +59335,12 @@ function waypointsToSvgPath(waypoints, cornerRadius) {
59243
59335
  const arcEnd = [curr[0] + uNext[0] * r, curr[1] + uNext[1] * r];
59244
59336
  const cross = dPrev[0] * dNext[1] - dPrev[1] * dNext[0];
59245
59337
  const sweep = cross > 0 ? 0 : 1;
59246
- path39 += ` L ${arcStart[0]},${arcStart[1]}`;
59247
- path39 += ` A ${r} ${r} 0 0 ${sweep} ${arcEnd[0]},${arcEnd[1]}`;
59338
+ path42 += ` L ${arcStart[0]},${arcStart[1]}`;
59339
+ path42 += ` A ${r} ${r} 0 0 ${sweep} ${arcEnd[0]},${arcEnd[1]}`;
59248
59340
  }
59249
59341
  const last2 = waypoints[waypoints.length - 1];
59250
- path39 += ` L ${last2[0]},${last2[1]}`;
59251
- return path39;
59342
+ path42 += ` L ${last2[0]},${last2[1]}`;
59343
+ return path42;
59252
59344
  }
59253
59345
  function computeWaypoints(from, to, nodeBoxes, sourceNodeId, targetNodeId, padding, exitStub, entryStub, allocator) {
59254
59346
  const isSelfConnection = sourceNodeId === targetNodeId;
@@ -59395,7 +59487,7 @@ function calculateOrthogonalPath(from, to, nodeBoxes, sourceNodeId, targetNodeId
59395
59487
  }
59396
59488
  function calculateOrthogonalPathSafe(from, to, nodeBoxes, sourceNodeId, targetNodeId, options, allocator) {
59397
59489
  try {
59398
- const path39 = calculateOrthogonalPath(
59490
+ const path42 = calculateOrthogonalPath(
59399
59491
  from,
59400
59492
  to,
59401
59493
  nodeBoxes,
@@ -59404,8 +59496,8 @@ function calculateOrthogonalPathSafe(from, to, nodeBoxes, sourceNodeId, targetNo
59404
59496
  options,
59405
59497
  allocator
59406
59498
  );
59407
- if (!path39 || path39.length < 5) return null;
59408
- return path39;
59499
+ if (!path42 || path42.length < 5) return null;
59500
+ return path42;
59409
59501
  } catch {
59410
59502
  return null;
59411
59503
  }
@@ -59600,13 +59692,13 @@ function computeConnectionPath(sx, sy, tx, ty) {
59600
59692
  const deUy = deY / deLen;
59601
59693
  const [cx, cy] = quadCurveControl(bx, by, dx, dy, -deUx, -deUy);
59602
59694
  const [fx, fy] = quadCurveControl(gx, gy, ex, ey, deUx, deUy);
59603
- let path39 = `M ${cx},${cy} M ${ax},${ay}`;
59604
- path39 += ` L ${bx},${by}`;
59605
- path39 += ` Q ${cx},${cy} ${dx},${dy}`;
59606
- path39 += ` L ${ex},${ey}`;
59607
- path39 += ` Q ${fx},${fy} ${gx},${gy}`;
59608
- path39 += ` L ${hx},${hy}`;
59609
- return path39;
59695
+ let path42 = `M ${cx},${cy} M ${ax},${ay}`;
59696
+ path42 += ` L ${bx},${by}`;
59697
+ path42 += ` Q ${cx},${cy} ${dx},${dy}`;
59698
+ path42 += ` L ${ex},${ey}`;
59699
+ path42 += ` Q ${fx},${fy} ${gx},${gy}`;
59700
+ path42 += ` L ${hx},${hy}`;
59701
+ return path42;
59610
59702
  }
59611
59703
  function orderedPorts(ports, direction) {
59612
59704
  const cloned = {};
@@ -59894,7 +59986,7 @@ function finalizeScopePositions(parentNode, ast, theme = "dark") {
59894
59986
  function buildConnection(fromNode, fromPort, toNode, toPort, sourcePort, targetPort, theme = "dark") {
59895
59987
  const sourceColor = getPortColor(sourcePort.dataType, sourcePort.isFailure, theme);
59896
59988
  const targetColor = getPortColor(targetPort.dataType, targetPort.isFailure, theme);
59897
- const path39 = computeConnectionPath(sourcePort.cx, sourcePort.cy, targetPort.cx, targetPort.cy);
59989
+ const path42 = computeConnectionPath(sourcePort.cx, sourcePort.cy, targetPort.cx, targetPort.cy);
59898
59990
  return {
59899
59991
  fromNode,
59900
59992
  fromPort,
@@ -59903,7 +59995,7 @@ function buildConnection(fromNode, fromPort, toNode, toPort, sourcePort, targetP
59903
59995
  sourceColor,
59904
59996
  targetColor,
59905
59997
  isStepConnection: sourcePort.dataType === "STEP",
59906
- path: path39
59998
+ path: path42
59907
59999
  };
59908
60000
  }
59909
60001
  function portsColumnHeight(count) {
@@ -60294,7 +60386,7 @@ function buildDiagramGraph(ast, options = {}) {
60294
60386
  const dy = ty - sy;
60295
60387
  const distance = Math.sqrt(dx * dx + dy * dy);
60296
60388
  const useCurve = forceCurveSet.has(pc);
60297
- let path39;
60389
+ let path42;
60298
60390
  if (!useCurve && distance > ORTHOGONAL_DISTANCE_THRESHOLD) {
60299
60391
  const orthoPath = calculateOrthogonalPathSafe(
60300
60392
  [sx, sy],
@@ -60305,9 +60397,9 @@ function buildDiagramGraph(ast, options = {}) {
60305
60397
  { fromPortIndex: pc.fromPortIndex, toPortIndex: pc.toPortIndex },
60306
60398
  allocator
60307
60399
  );
60308
- path39 = orthoPath ?? computeConnectionPath(sx, sy, tx, ty);
60400
+ path42 = orthoPath ?? computeConnectionPath(sx, sy, tx, ty);
60309
60401
  } else {
60310
- path39 = computeConnectionPath(sx, sy, tx, ty);
60402
+ path42 = computeConnectionPath(sx, sy, tx, ty);
60311
60403
  }
60312
60404
  const sourceColor = getPortColor(pc.sourcePort.dataType, pc.sourcePort.isFailure, themeName);
60313
60405
  const targetColor = getPortColor(pc.targetPort.dataType, pc.targetPort.isFailure, themeName);
@@ -60319,7 +60411,7 @@ function buildDiagramGraph(ast, options = {}) {
60319
60411
  sourceColor,
60320
60412
  targetColor,
60321
60413
  isStepConnection: pc.sourcePort.dataType === "STEP",
60322
- path: path39
60414
+ path: path42
60323
60415
  });
60324
60416
  }
60325
60417
  for (const node of nodes) {
@@ -60392,12 +60484,12 @@ function resolveDefaultIcon(nt) {
60392
60484
  if (nt.variant === "WORKFLOW" || nt.variant === "IMPORTED_WORKFLOW") return "flow";
60393
60485
  return "code";
60394
60486
  }
60395
- function pathExtent(path39) {
60487
+ function pathExtent(path42) {
60396
60488
  let minX = Infinity, minY = Infinity;
60397
60489
  let maxX = -Infinity, maxY = -Infinity;
60398
60490
  const pattern = /(-?[\d.]+),(-?[\d.]+)/g;
60399
60491
  let m;
60400
- while ((m = pattern.exec(path39)) !== null) {
60492
+ while ((m = pattern.exec(path42)) !== null) {
60401
60493
  const x = parseFloat(m[1]);
60402
60494
  const y = parseFloat(m[2]);
60403
60495
  minX = Math.min(minX, x);
@@ -60501,7 +60593,7 @@ function renderSVG(graph, options = {}) {
60501
60593
  function renderConnection(parts2, conn, gradIndex) {
60502
60594
  const dashAttr = conn.isStepConnection ? "" : ' stroke-dasharray="8 4"';
60503
60595
  parts2.push(
60504
- ` <path d="${conn.path}" fill="none" stroke="url(#conn-grad-${gradIndex})" stroke-width="3"${dashAttr} stroke-linecap="round" data-source="${escapeXml(conn.fromNode)}.${escapeXml(conn.fromPort)}" data-target="${escapeXml(conn.toNode)}.${escapeXml(conn.toPort)}"/>`
60596
+ ` <path d="${conn.path}" fill="none" stroke="url(#conn-grad-${gradIndex})" stroke-width="3"${dashAttr} stroke-linecap="round" data-source="${escapeXml(conn.fromNode)}.${escapeXml(conn.fromPort)}:output" data-target="${escapeXml(conn.toNode)}.${escapeXml(conn.toPort)}:input"/>`
60505
60597
  );
60506
60598
  }
60507
60599
  function renderScopeConnection(parts2, conn, allConnections) {
@@ -60509,7 +60601,7 @@ function renderScopeConnection(parts2, conn, allConnections) {
60509
60601
  if (gradIndex < 0) return;
60510
60602
  const dashAttr = conn.isStepConnection ? "" : ' stroke-dasharray="8 4"';
60511
60603
  parts2.push(
60512
- ` <path d="${conn.path}" fill="none" stroke="url(#conn-grad-${gradIndex})" stroke-width="2.5"${dashAttr} stroke-linecap="round" data-source="${escapeXml(conn.fromNode)}.${escapeXml(conn.fromPort)}" data-target="${escapeXml(conn.toNode)}.${escapeXml(conn.toPort)}"/>`
60604
+ ` <path d="${conn.path}" fill="none" stroke="url(#conn-grad-${gradIndex})" stroke-width="2.5"${dashAttr} stroke-linecap="round" data-source="${escapeXml(conn.fromNode)}.${escapeXml(conn.fromPort)}:output" data-target="${escapeXml(conn.toNode)}.${escapeXml(conn.toPort)}:input"/>`
60513
60605
  );
60514
60606
  }
60515
60607
  function renderNodeBody(parts2, node, theme, indent) {
@@ -60590,7 +60682,7 @@ function renderPortDots(parts2, nodeId, inputs, outputs, themeName) {
60590
60682
  const color = getPortColor(port.dataType, port.isFailure, themeName);
60591
60683
  const ringColor = getPortRingColor(port.dataType, port.isFailure, themeName);
60592
60684
  const dir = port.direction === "INPUT" ? "input" : "output";
60593
- parts2.push(` <circle cx="${port.cx}" cy="${port.cy}" r="${PORT_RADIUS}" fill="${color}" stroke="${ringColor}" stroke-width="2" data-port-id="${escapeXml(nodeId)}.${escapeXml(port.name)}" data-direction="${dir}"/>`);
60685
+ parts2.push(` <circle cx="${port.cx}" cy="${port.cy}" r="${PORT_RADIUS}" fill="${color}" stroke="${ringColor}" stroke-width="2" data-port-id="${escapeXml(nodeId)}.${escapeXml(port.name)}:${dir}" data-direction="${dir}"/>`);
60594
60686
  }
60595
60687
  }
60596
60688
  function renderPortLabels(parts2, nodeId, inputs, outputs, theme, themeName) {
@@ -60598,7 +60690,8 @@ function renderPortLabels(parts2, nodeId, inputs, outputs, theme, themeName) {
60598
60690
  const color = getPortColor(port.dataType, port.isFailure, themeName);
60599
60691
  const isInput = port.direction === "INPUT";
60600
60692
  const abbrev = TYPE_ABBREVIATIONS[port.dataType] ?? port.dataType;
60601
- const portId = `${escapeXml(nodeId)}.${escapeXml(port.name)}`;
60693
+ const dir = isInput ? "input" : "output";
60694
+ const portId = `${escapeXml(nodeId)}.${escapeXml(port.name)}:${dir}`;
60602
60695
  const portLabel = port.label;
60603
60696
  const typeWidth = measureText(abbrev);
60604
60697
  const labelWidth = measureText(portLabel);
@@ -60892,43 +60985,79 @@ body.node-active .connections path.dimmed { opacity: 0.15; }
60892
60985
  else if (e.key === 'Escape') deselectNode();
60893
60986
  });
60894
60987
 
60895
- // ---- Port label visibility via JS (since CSS sibling selectors can't reach .labels group) ----
60896
- var labelEls = content.querySelectorAll('.labels g[data-port-label]');
60897
- var nodeEls = content.querySelectorAll('.nodes g[data-node-id]');
60988
+ // ---- Port label visibility ----
60989
+ var labelMap = {};
60990
+ content.querySelectorAll('.labels g[data-port-label]').forEach(function(lbl) {
60991
+ labelMap[lbl.getAttribute('data-port-label')] = lbl;
60992
+ });
60898
60993
 
60899
- function showLabelsFor(id) {
60900
- labelEls.forEach(function(lbl) {
60901
- var portId = lbl.getAttribute('data-port-label') || '';
60902
- if (portId.indexOf(id + '.') === 0) {
60903
- lbl.style.opacity = '1';
60904
- lbl.style.pointerEvents = 'auto';
60905
- }
60994
+ // Build adjacency: portId \u2192 array of connected portIds
60995
+ var portConnections = {};
60996
+ content.querySelectorAll('.connections path').forEach(function(p) {
60997
+ var src = p.getAttribute('data-source');
60998
+ var tgt = p.getAttribute('data-target');
60999
+ if (!src || !tgt) return;
61000
+ if (!portConnections[src]) portConnections[src] = [];
61001
+ if (!portConnections[tgt]) portConnections[tgt] = [];
61002
+ portConnections[src].push(tgt);
61003
+ portConnections[tgt].push(src);
61004
+ });
61005
+
61006
+ var allLabelIds = Object.keys(labelMap);
61007
+ var hoveredPort = null;
61008
+
61009
+ function showLabel(id) { var l = labelMap[id]; if (l) { l.style.opacity = '1'; l.style.pointerEvents = 'auto'; } }
61010
+ function hideLabel(id) { var l = labelMap[id]; if (l) { l.style.opacity = '0'; l.style.pointerEvents = 'none'; } }
61011
+
61012
+ function showLabelsFor(nodeId) {
61013
+ allLabelIds.forEach(function(id) {
61014
+ if (id.indexOf(nodeId + '.') === 0) showLabel(id);
60906
61015
  });
60907
61016
  }
60908
- function hideLabelsFor(id) {
60909
- labelEls.forEach(function(lbl) {
60910
- var portId = lbl.getAttribute('data-port-label') || '';
60911
- if (portId.indexOf(id + '.') === 0) {
60912
- lbl.style.opacity = '0';
60913
- lbl.style.pointerEvents = 'none';
60914
- }
61017
+ function hideLabelsFor(nodeId) {
61018
+ allLabelIds.forEach(function(id) {
61019
+ if (id.indexOf(nodeId + '.') === 0) hideLabel(id);
60915
61020
  });
60916
61021
  }
60917
61022
 
61023
+ // Node hover: show all port labels for the hovered node
61024
+ var nodeEls = content.querySelectorAll('.nodes g[data-node-id]');
60918
61025
  nodeEls.forEach(function(nodeG) {
60919
61026
  var nodeId = nodeG.getAttribute('data-node-id');
60920
61027
  var parentNodeG = nodeG.parentElement ? nodeG.parentElement.closest('g[data-node-id]') : null;
60921
61028
  var parentId = parentNodeG ? parentNodeG.getAttribute('data-node-id') : null;
60922
61029
  nodeG.addEventListener('mouseenter', function() {
61030
+ if (hoveredPort) return; // port hover takes priority
60923
61031
  if (parentId) hideLabelsFor(parentId);
60924
61032
  showLabelsFor(nodeId);
60925
61033
  });
60926
61034
  nodeG.addEventListener('mouseleave', function() {
61035
+ if (hoveredPort) return;
60927
61036
  hideLabelsFor(nodeId);
60928
61037
  if (parentId) showLabelsFor(parentId);
60929
61038
  });
60930
61039
  });
60931
61040
 
61041
+ // Port hover: show this port's label + all connected port labels
61042
+ content.querySelectorAll('[data-port-id]').forEach(function(portEl) {
61043
+ var portId = portEl.getAttribute('data-port-id');
61044
+ var nodeId = portId.split('.')[0];
61045
+ var peers = (portConnections[portId] || []).concat(portId);
61046
+
61047
+ portEl.addEventListener('mouseenter', function() {
61048
+ hoveredPort = portId;
61049
+ // Hide all labels for this node first, then show only the relevant ones
61050
+ hideLabelsFor(nodeId);
61051
+ peers.forEach(showLabel);
61052
+ });
61053
+ portEl.addEventListener('mouseleave', function() {
61054
+ hoveredPort = null;
61055
+ peers.forEach(hideLabel);
61056
+ // Restore all labels for the node since we're still inside it
61057
+ showLabelsFor(nodeId);
61058
+ });
61059
+ });
61060
+
60932
61061
  // ---- Click to inspect node ----
60933
61062
  function deselectNode() {
60934
61063
  selectedNodeId = null;
@@ -60955,7 +61084,7 @@ body.node-active .connections path.dimmed { opacity: 0.15; }
60955
61084
  ports.forEach(function(p) {
60956
61085
  var id = p.getAttribute('data-port-id');
60957
61086
  var dir = p.getAttribute('data-direction');
60958
- var name = id.split('.').slice(1).join('.');
61087
+ var name = id.split('.').slice(1).join('.').replace(/:(?:input|output)$/, '');
60959
61088
  if (dir === 'input') inputs.push(name);
60960
61089
  else outputs.push(name);
60961
61090
  });
@@ -63442,13 +63571,13 @@ var PromisePolyfill = class extends Promise {
63442
63571
  // Available starting from Node 22
63443
63572
  // https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Promise/withResolvers
63444
63573
  static withResolver() {
63445
- let resolve28;
63574
+ let resolve31;
63446
63575
  let reject2;
63447
63576
  const promise = new Promise((res, rej) => {
63448
- resolve28 = res;
63577
+ resolve31 = res;
63449
63578
  reject2 = rej;
63450
63579
  });
63451
- return { promise, resolve: resolve28, reject: reject2 };
63580
+ return { promise, resolve: resolve31, reject: reject2 };
63452
63581
  }
63453
63582
  };
63454
63583
 
@@ -63482,7 +63611,7 @@ function createPrompt(view) {
63482
63611
  output
63483
63612
  });
63484
63613
  const screen = new ScreenManager(rl);
63485
- const { promise, resolve: resolve28, reject: reject2 } = PromisePolyfill.withResolver();
63614
+ const { promise, resolve: resolve31, reject: reject2 } = PromisePolyfill.withResolver();
63486
63615
  const cancel = () => reject2(new CancelPromptError());
63487
63616
  if (signal) {
63488
63617
  const abort = () => reject2(new AbortPromptError({ cause: signal.reason }));
@@ -63509,7 +63638,7 @@ function createPrompt(view) {
63509
63638
  cycle(() => {
63510
63639
  try {
63511
63640
  const nextView = view(config2, (value2) => {
63512
- setImmediate(() => resolve28(value2));
63641
+ setImmediate(() => resolve31(value2));
63513
63642
  });
63514
63643
  if (nextView === void 0) {
63515
63644
  const callerFilename = callSites[1]?.getFileName();
@@ -64090,13 +64219,13 @@ var PromisePolyfill2 = class extends Promise {
64090
64219
  // Available starting from Node 22
64091
64220
  // https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Promise/withResolvers
64092
64221
  static withResolver() {
64093
- let resolve28;
64222
+ let resolve31;
64094
64223
  let reject2;
64095
64224
  const promise = new Promise((res, rej) => {
64096
- resolve28 = res;
64225
+ resolve31 = res;
64097
64226
  reject2 = rej;
64098
64227
  });
64099
- return { promise, resolve: resolve28, reject: reject2 };
64228
+ return { promise, resolve: resolve31, reject: reject2 };
64100
64229
  }
64101
64230
  };
64102
64231
 
@@ -64130,7 +64259,7 @@ function createPrompt2(view) {
64130
64259
  output
64131
64260
  });
64132
64261
  const screen = new ScreenManager2(rl);
64133
- const { promise, resolve: resolve28, reject: reject2 } = PromisePolyfill2.withResolver();
64262
+ const { promise, resolve: resolve31, reject: reject2 } = PromisePolyfill2.withResolver();
64134
64263
  const cancel = () => reject2(new CancelPromptError2());
64135
64264
  if (signal) {
64136
64265
  const abort = () => reject2(new AbortPromptError2({ cause: signal.reason }));
@@ -64157,7 +64286,7 @@ function createPrompt2(view) {
64157
64286
  cycle(() => {
64158
64287
  try {
64159
64288
  const nextView = view(config2, (value2) => {
64160
- setImmediate(() => resolve28(value2));
64289
+ setImmediate(() => resolve31(value2));
64161
64290
  });
64162
64291
  if (nextView === void 0) {
64163
64292
  const callerFilename = callSites[1]?.getFileName();
@@ -64709,13 +64838,13 @@ var PromisePolyfill3 = class extends Promise {
64709
64838
  // Available starting from Node 22
64710
64839
  // https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Promise/withResolvers
64711
64840
  static withResolver() {
64712
- let resolve28;
64841
+ let resolve31;
64713
64842
  let reject2;
64714
64843
  const promise = new Promise((res, rej) => {
64715
- resolve28 = res;
64844
+ resolve31 = res;
64716
64845
  reject2 = rej;
64717
64846
  });
64718
- return { promise, resolve: resolve28, reject: reject2 };
64847
+ return { promise, resolve: resolve31, reject: reject2 };
64719
64848
  }
64720
64849
  };
64721
64850
 
@@ -64749,7 +64878,7 @@ function createPrompt3(view) {
64749
64878
  output
64750
64879
  });
64751
64880
  const screen = new ScreenManager3(rl);
64752
- const { promise, resolve: resolve28, reject: reject2 } = PromisePolyfill3.withResolver();
64881
+ const { promise, resolve: resolve31, reject: reject2 } = PromisePolyfill3.withResolver();
64753
64882
  const cancel = () => reject2(new CancelPromptError3());
64754
64883
  if (signal) {
64755
64884
  const abort = () => reject2(new AbortPromptError3({ cause: signal.reason }));
@@ -64776,7 +64905,7 @@ function createPrompt3(view) {
64776
64905
  cycle(() => {
64777
64906
  try {
64778
64907
  const nextView = view(config2, (value2) => {
64779
- setImmediate(() => resolve28(value2));
64908
+ setImmediate(() => resolve31(value2));
64780
64909
  });
64781
64910
  if (nextView === void 0) {
64782
64911
  const callerFilename = callSites[1]?.getFileName();
@@ -67275,12 +67404,12 @@ function parse4(str2) {
67275
67404
  uri.queryKey = queryKey(uri, uri["query"]);
67276
67405
  return uri;
67277
67406
  }
67278
- function pathNames(obj, path39) {
67279
- const regx = /\/{2,9}/g, names = path39.replace(regx, "/").split("/");
67280
- if (path39.slice(0, 1) == "/" || path39.length === 0) {
67407
+ function pathNames(obj, path42) {
67408
+ const regx = /\/{2,9}/g, names = path42.replace(regx, "/").split("/");
67409
+ if (path42.slice(0, 1) == "/" || path42.length === 0) {
67281
67410
  names.splice(0, 1);
67282
67411
  }
67283
- if (path39.slice(-1) == "/") {
67412
+ if (path42.slice(-1) == "/") {
67284
67413
  names.splice(names.length - 1, 1);
67285
67414
  }
67286
67415
  return names;
@@ -67898,7 +68027,7 @@ var protocol2 = Socket.protocol;
67898
68027
  // node_modules/socket.io-client/build/esm-debug/url.js
67899
68028
  var import_debug7 = __toESM(require_src(), 1);
67900
68029
  var debug7 = (0, import_debug7.default)("socket.io-client:url");
67901
- function url(uri, path39 = "", loc) {
68030
+ function url(uri, path42 = "", loc) {
67902
68031
  let obj = uri;
67903
68032
  loc = loc || typeof location !== "undefined" && location;
67904
68033
  if (null == uri)
@@ -67932,7 +68061,7 @@ function url(uri, path39 = "", loc) {
67932
68061
  obj.path = obj.path || "/";
67933
68062
  const ipv62 = obj.host.indexOf(":") !== -1;
67934
68063
  const host = ipv62 ? "[" + obj.host + "]" : obj.host;
67935
- obj.id = obj.protocol + "://" + host + ":" + obj.port + path39;
68064
+ obj.id = obj.protocol + "://" + host + ":" + obj.port + path42;
67936
68065
  obj.href = obj.protocol + "://" + host + (loc && loc.port === obj.port ? "" : ":" + obj.port);
67937
68066
  return obj;
67938
68067
  }
@@ -68584,9 +68713,9 @@ var Socket2 = class extends import_component_emitter5.Emitter {
68584
68713
  * @return a Promise that will be fulfilled when the server acknowledges the event
68585
68714
  */
68586
68715
  emitWithAck(ev, ...args) {
68587
- return new Promise((resolve28, reject2) => {
68716
+ return new Promise((resolve31, reject2) => {
68588
68717
  const fn = (arg1, arg2) => {
68589
- return arg1 ? reject2(arg1) : resolve28(arg2);
68718
+ return arg1 ? reject2(arg1) : resolve31(arg2);
68590
68719
  };
68591
68720
  fn.withError = true;
68592
68721
  args.push(fn);
@@ -69559,8 +69688,8 @@ function lookup(uri, opts) {
69559
69688
  const parsed = url(uri, opts.path || "/socket.io");
69560
69689
  const source = parsed.source;
69561
69690
  const id = parsed.id;
69562
- const path39 = parsed.path;
69563
- const sameNamespace = cache[id] && path39 in cache[id]["nsps"];
69691
+ const path42 = parsed.path;
69692
+ const sameNamespace = cache[id] && path42 in cache[id]["nsps"];
69564
69693
  const newConnection = opts.forceNew || opts["force new connection"] || false === opts.multiplex || sameNamespace;
69565
69694
  let io;
69566
69695
  if (newConnection) {
@@ -70104,8 +70233,8 @@ function getErrorMap() {
70104
70233
 
70105
70234
  // node_modules/zod/v3/helpers/parseUtil.js
70106
70235
  var makeIssue = (params) => {
70107
- const { data, path: path39, errorMaps, issueData } = params;
70108
- const fullPath = [...path39, ...issueData.path || []];
70236
+ const { data, path: path42, errorMaps, issueData } = params;
70237
+ const fullPath = [...path42, ...issueData.path || []];
70109
70238
  const fullIssue = {
70110
70239
  ...issueData,
70111
70240
  path: fullPath
@@ -70221,11 +70350,11 @@ var errorUtil;
70221
70350
 
70222
70351
  // node_modules/zod/v3/types.js
70223
70352
  var ParseInputLazyPath = class {
70224
- constructor(parent, value2, path39, key) {
70353
+ constructor(parent, value2, path42, key) {
70225
70354
  this._cachedPath = [];
70226
70355
  this.parent = parent;
70227
70356
  this.data = value2;
70228
- this._path = path39;
70357
+ this._path = path42;
70229
70358
  this._key = key;
70230
70359
  }
70231
70360
  get path() {
@@ -73862,10 +73991,10 @@ function assignProp(target, prop, value2) {
73862
73991
  configurable: true
73863
73992
  });
73864
73993
  }
73865
- function getElementAtPath(obj, path39) {
73866
- if (!path39)
73994
+ function getElementAtPath(obj, path42) {
73995
+ if (!path42)
73867
73996
  return obj;
73868
- return path39.reduce((acc, key) => acc?.[key], obj);
73997
+ return path42.reduce((acc, key) => acc?.[key], obj);
73869
73998
  }
73870
73999
  function promiseAllObject(promisesObj) {
73871
74000
  const keys2 = Object.keys(promisesObj);
@@ -74185,11 +74314,11 @@ function aborted(x, startIndex = 0) {
74185
74314
  }
74186
74315
  return false;
74187
74316
  }
74188
- function prefixIssues(path39, issues) {
74317
+ function prefixIssues(path42, issues) {
74189
74318
  return issues.map((iss) => {
74190
74319
  var _a;
74191
74320
  (_a = iss).path ?? (_a.path = []);
74192
- iss.path.unshift(path39);
74321
+ iss.path.unshift(path42);
74193
74322
  return iss;
74194
74323
  });
74195
74324
  }
@@ -81698,7 +81827,7 @@ var Protocol = class {
81698
81827
  return;
81699
81828
  }
81700
81829
  const pollInterval = task2.pollInterval ?? this._options?.defaultTaskPollInterval ?? 1e3;
81701
- await new Promise((resolve28) => setTimeout(resolve28, pollInterval));
81830
+ await new Promise((resolve31) => setTimeout(resolve31, pollInterval));
81702
81831
  options?.signal?.throwIfAborted();
81703
81832
  }
81704
81833
  } catch (error2) {
@@ -81715,7 +81844,7 @@ var Protocol = class {
81715
81844
  */
81716
81845
  request(request, resultSchema, options) {
81717
81846
  const { relatedRequestId, resumptionToken, onresumptiontoken, task, relatedTask } = options ?? {};
81718
- return new Promise((resolve28, reject2) => {
81847
+ return new Promise((resolve31, reject2) => {
81719
81848
  const earlyReject = (error2) => {
81720
81849
  reject2(error2);
81721
81850
  };
@@ -81793,7 +81922,7 @@ var Protocol = class {
81793
81922
  if (!parseResult.success) {
81794
81923
  reject2(parseResult.error);
81795
81924
  } else {
81796
- resolve28(parseResult.data);
81925
+ resolve31(parseResult.data);
81797
81926
  }
81798
81927
  } catch (error2) {
81799
81928
  reject2(error2);
@@ -82054,12 +82183,12 @@ var Protocol = class {
82054
82183
  }
82055
82184
  } catch {
82056
82185
  }
82057
- return new Promise((resolve28, reject2) => {
82186
+ return new Promise((resolve31, reject2) => {
82058
82187
  if (signal.aborted) {
82059
82188
  reject2(new McpError(ErrorCode.InvalidRequest, "Request cancelled"));
82060
82189
  return;
82061
82190
  }
82062
- const timeoutId = setTimeout(resolve28, interval);
82191
+ const timeoutId = setTimeout(resolve31, interval);
82063
82192
  signal.addEventListener("abort", () => {
82064
82193
  clearTimeout(timeoutId);
82065
82194
  reject2(new McpError(ErrorCode.InvalidRequest, "Request cancelled"));
@@ -83018,7 +83147,7 @@ var McpServer = class {
83018
83147
  let task = createTaskResult.task;
83019
83148
  const pollInterval = task.pollInterval ?? 5e3;
83020
83149
  while (task.status !== "completed" && task.status !== "failed" && task.status !== "cancelled") {
83021
- await new Promise((resolve28) => setTimeout(resolve28, pollInterval));
83150
+ await new Promise((resolve31) => setTimeout(resolve31, pollInterval));
83022
83151
  const updatedTask = await extra.taskStore.getTask(taskId);
83023
83152
  if (!updatedTask) {
83024
83153
  throw new McpError(ErrorCode.InternalError, `Task ${taskId} not found during polling`);
@@ -83661,12 +83790,12 @@ var StdioServerTransport = class {
83661
83790
  this.onclose?.();
83662
83791
  }
83663
83792
  send(message) {
83664
- return new Promise((resolve28) => {
83793
+ return new Promise((resolve31) => {
83665
83794
  const json2 = serializeMessage(message);
83666
83795
  if (this._stdout.write(json2)) {
83667
- resolve28();
83796
+ resolve31();
83668
83797
  } else {
83669
- this._stdout.once("drain", resolve28);
83798
+ this._stdout.once("drain", resolve31);
83670
83799
  }
83671
83800
  });
83672
83801
  }
@@ -83880,17 +84009,17 @@ var EditorConnection = class {
83880
84009
  return { requestId: "", success: false, error: "Not connected" };
83881
84010
  }
83882
84011
  const requestId = `${Date.now()}-${Math.random().toString(36).slice(2, 8)}`;
83883
- return new Promise((resolve28) => {
84012
+ return new Promise((resolve31) => {
83884
84013
  const handler = (data) => {
83885
84014
  if (data.requestId === requestId) {
83886
84015
  clearTimeout(timeout);
83887
84016
  this.socket.off("fw:ack", handler);
83888
- resolve28(data);
84017
+ resolve31(data);
83889
84018
  }
83890
84019
  };
83891
84020
  const timeout = setTimeout(() => {
83892
84021
  this.socket.off("fw:ack", handler);
83893
- resolve28({ requestId, success: false, error: "Timeout" });
84022
+ resolve31({ requestId, success: false, error: "Timeout" });
83894
84023
  }, this.ackTimeout);
83895
84024
  this.socket.on("fw:ack", handler);
83896
84025
  this.socket.emit("integration:command", { requestId, action, params });
@@ -83907,17 +84036,17 @@ var EditorConnection = class {
83907
84036
  return { requestId: "", success: false, error: "Not connected" };
83908
84037
  }
83909
84038
  const requestId = `${Date.now()}-${Math.random().toString(36).slice(2, 8)}`;
83910
- return new Promise((resolve28) => {
84039
+ return new Promise((resolve31) => {
83911
84040
  const handler = (data) => {
83912
84041
  if (data.requestId === requestId) {
83913
84042
  clearTimeout(timeout);
83914
84043
  this.socket.off("fw:ack", handler);
83915
- resolve28(data);
84044
+ resolve31(data);
83916
84045
  }
83917
84046
  };
83918
84047
  const timeout = setTimeout(() => {
83919
84048
  this.socket.off("fw:ack", handler);
83920
- resolve28({ requestId, success: false, error: "Timeout" });
84049
+ resolve31({ requestId, success: false, error: "Timeout" });
83921
84050
  }, this.ackTimeout);
83922
84051
  this.socket.on("fw:ack", handler);
83923
84052
  this.socket.emit("integration:batch", { requestId, commands });
@@ -83945,11 +84074,11 @@ function defaultRegistrationDeps() {
83945
84074
  return { stdout: "", exitCode: 1 };
83946
84075
  }
83947
84076
  },
83948
- prompt: (question) => new Promise((resolve28) => {
84077
+ prompt: (question) => new Promise((resolve31) => {
83949
84078
  const rl = readline8.createInterface({ input: process.stdin, output: process.stderr });
83950
84079
  rl.question(question, (answer) => {
83951
84080
  rl.close();
83952
- resolve28(answer.trim().toLowerCase());
84081
+ resolve31(answer.trim().toLowerCase());
83953
84082
  });
83954
84083
  }),
83955
84084
  log: (msg) => process.stderr.write(msg + "\n"),
@@ -84066,8 +84195,8 @@ var AgentChannel = class {
84066
84195
  */
84067
84196
  async request(agentRequest) {
84068
84197
  this._pauseResolve?.(agentRequest);
84069
- return new Promise((resolve28, reject2) => {
84070
- this._resolve = resolve28;
84198
+ return new Promise((resolve31, reject2) => {
84199
+ this._resolve = resolve31;
84071
84200
  this._reject = reject2;
84072
84201
  });
84073
84202
  }
@@ -84097,8 +84226,8 @@ var AgentChannel = class {
84097
84226
  this._pausePromise = this._createPausePromise();
84098
84227
  }
84099
84228
  _createPausePromise() {
84100
- return new Promise((resolve28) => {
84101
- this._pauseResolve = resolve28;
84229
+ return new Promise((resolve31) => {
84230
+ this._pauseResolve = resolve31;
84102
84231
  });
84103
84232
  }
84104
84233
  };
@@ -84650,8 +84779,8 @@ ${parseResult.errors.join("\n")}`);
84650
84779
  });
84651
84780
  const outputFile = filePath.replace(/\.ts$/, ".inngest.ts");
84652
84781
  if (args.write !== false) {
84653
- const fs38 = await import("fs");
84654
- fs38.writeFileSync(outputFile, code, "utf8");
84782
+ const fs41 = await import("fs");
84783
+ fs41.writeFileSync(outputFile, code, "utf8");
84655
84784
  }
84656
84785
  return makeToolResult({
84657
84786
  target: "inngest",
@@ -86081,8 +86210,8 @@ var OpenAPIGenerator = class {
86081
86210
  doc.paths["/health"] = this.generateHealthEndpoint();
86082
86211
  doc.paths["/workflows"] = this.generateListEndpoint();
86083
86212
  for (const endpoint of endpoints) {
86084
- const path39 = options.basePath ? `${options.basePath}${endpoint.path}` : endpoint.path;
86085
- doc.paths[path39] = this.generateWorkflowEndpoint(endpoint);
86213
+ const path42 = options.basePath ? `${options.basePath}${endpoint.path}` : endpoint.path;
86214
+ doc.paths[path42] = this.generateWorkflowEndpoint(endpoint);
86086
86215
  }
86087
86216
  return doc;
86088
86217
  }
@@ -86459,8 +86588,8 @@ var BaseExportTarget = class {
86459
86588
  * Get relative import path for the workflow
86460
86589
  */
86461
86590
  getWorkflowImport(workflowFile) {
86462
- const basename17 = path24.basename(workflowFile, path24.extname(workflowFile));
86463
- return `./${basename17}.js`;
86591
+ const basename18 = path24.basename(workflowFile, path24.extname(workflowFile));
86592
+ return `./${basename18}.js`;
86464
86593
  }
86465
86594
  /**
86466
86595
  * Generate OpenAPI spec for node types as HTTP endpoints
@@ -91973,6 +92102,249 @@ function registerDocsTools(mcp) {
91973
92102
  );
91974
92103
  }
91975
92104
 
92105
+ // src/mcp/tools-model.ts
92106
+ import * as fs28 from "fs";
92107
+ import * as path31 from "path";
92108
+ var stepSchema = external_exports.object({
92109
+ name: external_exports.string().describe("Function name for this node"),
92110
+ description: external_exports.string().optional().describe("Brief description of what this node does"),
92111
+ inputs: external_exports.record(external_exports.string()).describe('Input ports as { portName: dataType } (e.g. { email: "STRING" })'),
92112
+ outputs: external_exports.record(external_exports.string()).describe("Output ports as { portName: dataType }")
92113
+ });
92114
+ function findDeclareFunction(source, functionName) {
92115
+ const lines = source.split("\n");
92116
+ const startPattern = new RegExp(`^(\\s*)declare\\s+function\\s+${escapeRegex2(functionName)}\\s*\\(`);
92117
+ for (let i = 0; i < lines.length; i++) {
92118
+ const m = lines[i].match(startPattern);
92119
+ if (!m) continue;
92120
+ const indent = m[1] || "";
92121
+ let accumulated = lines[i];
92122
+ let j = i;
92123
+ while (!accumulated.trimEnd().endsWith(";") && j < lines.length - 1) {
92124
+ j++;
92125
+ accumulated += "\n" + lines[j];
92126
+ }
92127
+ return { match: accumulated, indent };
92128
+ }
92129
+ return null;
92130
+ }
92131
+ function registerModelTools(mcp) {
92132
+ mcp.tool(
92133
+ "fw_create_model",
92134
+ "Create a new stub workflow model from a structured description. Generates a TypeScript file with declare function stubs and workflow annotations. The model can be validated structurally before any node is implemented.",
92135
+ {
92136
+ name: external_exports.string().describe("Workflow name (used as export name)"),
92137
+ description: external_exports.string().optional().describe("Workflow description"),
92138
+ steps: external_exports.array(stepSchema).min(1).describe("Node definitions in execution order"),
92139
+ flow: external_exports.string().describe('Execution path, e.g. "Start -> validateEmail -> checkUserExists -> Exit"'),
92140
+ filePath: external_exports.string().describe("Output file path")
92141
+ },
92142
+ async (args) => {
92143
+ try {
92144
+ const outputPath = path31.resolve(args.filePath);
92145
+ const lines = [];
92146
+ for (const step of args.steps) {
92147
+ lines.push("/** @flowWeaver node */");
92148
+ const params = Object.entries(step.inputs).map(([name, type2]) => `${name}: ${mapTypeToTS(type2)}`).join(", ");
92149
+ const outputEntries = Object.entries(step.outputs);
92150
+ const returnType = outputEntries.length === 1 ? mapTypeToTS(outputEntries[0][1]) : `{ ${outputEntries.map(([name, type2]) => `${name}: ${mapTypeToTS(type2)}`).join("; ")} }`;
92151
+ lines.push(`declare function ${step.name}(${params}): ${returnType};`);
92152
+ lines.push("");
92153
+ }
92154
+ const flowSteps = args.flow.split("->").map((s) => s.trim()).filter(Boolean);
92155
+ const nodeAnnotations = args.steps.map((step) => `@node ${step.name} ${step.name}`);
92156
+ const pathAnnotation = `@path ${flowSteps.join(" -> ")}`;
92157
+ const jsdocLines = ["/**"];
92158
+ if (args.description) {
92159
+ jsdocLines.push(` * ${args.description}`);
92160
+ jsdocLines.push(" *");
92161
+ }
92162
+ jsdocLines.push(" * @flowWeaver workflow @autoConnect");
92163
+ for (const nodeAnn of nodeAnnotations) {
92164
+ jsdocLines.push(` * ${nodeAnn}`);
92165
+ }
92166
+ jsdocLines.push(` * ${pathAnnotation}`);
92167
+ jsdocLines.push(" */");
92168
+ jsdocLines.push(`export const ${args.name} = 'flowWeaver:draft';`);
92169
+ lines.push(...jsdocLines);
92170
+ lines.push("");
92171
+ const content = lines.join("\n");
92172
+ const dir = path31.dirname(outputPath);
92173
+ if (!fs28.existsSync(dir)) {
92174
+ fs28.mkdirSync(dir, { recursive: true });
92175
+ }
92176
+ fs28.writeFileSync(outputPath, content, "utf8");
92177
+ return makeToolResult({
92178
+ filePath: outputPath,
92179
+ workflowName: args.name,
92180
+ stubCount: args.steps.length,
92181
+ nodes: args.steps.map((s) => s.name)
92182
+ });
92183
+ } catch (err) {
92184
+ return makeErrorResult(
92185
+ "CREATE_MODEL_ERROR",
92186
+ `fw_create_model failed: ${err instanceof Error ? err.message : String(err)}`
92187
+ );
92188
+ }
92189
+ }
92190
+ );
92191
+ mcp.tool(
92192
+ "fw_workflow_status",
92193
+ "Report implementation progress for a workflow \u2014 which nodes are stubs, which are implemented, and whether the graph structure is valid.",
92194
+ {
92195
+ filePath: external_exports.string().describe("Path to the workflow file"),
92196
+ workflowName: external_exports.string().optional().describe("Specific workflow name if file has multiple")
92197
+ },
92198
+ async (args) => {
92199
+ try {
92200
+ const filePath = path31.resolve(args.filePath);
92201
+ const parseResult = await parseWorkflow(filePath, { workflowName: args.workflowName });
92202
+ if (parseResult.errors.length > 0) {
92203
+ return makeErrorResult("PARSE_ERROR", `Parse errors:
92204
+ ${parseResult.errors.join("\n")}`);
92205
+ }
92206
+ const ast = parseResult.ast;
92207
+ const instanceTypeMap = /* @__PURE__ */ new Map();
92208
+ for (const nt of ast.nodeTypes) {
92209
+ instanceTypeMap.set(nt.name, nt);
92210
+ if (nt.functionName !== nt.name) {
92211
+ instanceTypeMap.set(nt.functionName, nt);
92212
+ }
92213
+ }
92214
+ const nodes = [];
92215
+ const seen = /* @__PURE__ */ new Set();
92216
+ for (const instance of ast.instances) {
92217
+ const nt = instanceTypeMap.get(instance.nodeType);
92218
+ if (!nt || seen.has(nt.functionName)) continue;
92219
+ seen.add(nt.functionName);
92220
+ const inputs = {};
92221
+ const outputs = {};
92222
+ for (const [name, port] of Object.entries(nt.inputs)) {
92223
+ if (name === "execute") continue;
92224
+ inputs[name] = port.dataType;
92225
+ }
92226
+ for (const [name, port] of Object.entries(nt.outputs)) {
92227
+ if (name === "onSuccess" || name === "onFailure") continue;
92228
+ outputs[name] = port.dataType;
92229
+ }
92230
+ nodes.push({
92231
+ name: nt.functionName,
92232
+ status: nt.variant === "STUB" ? "stub" : "implemented",
92233
+ inputs,
92234
+ outputs
92235
+ });
92236
+ }
92237
+ const implemented = nodes.filter((n) => n.status === "implemented").length;
92238
+ const total = nodes.length;
92239
+ const validation = validateWorkflow(ast, { mode: "draft" });
92240
+ const structuralErrors = validation.errors.filter((e) => e.code !== "STUB_NODE").map((e) => ({ message: e.message, code: e.code, node: e.node }));
92241
+ return makeToolResult({
92242
+ workflowName: ast.name,
92243
+ implemented,
92244
+ total,
92245
+ percentage: total > 0 ? Math.round(implemented / total * 100) : 100,
92246
+ nodes,
92247
+ structurallyValid: structuralErrors.length === 0,
92248
+ structuralErrors
92249
+ });
92250
+ } catch (err) {
92251
+ return makeErrorResult(
92252
+ "STATUS_ERROR",
92253
+ `fw_workflow_status failed: ${err instanceof Error ? err.message : String(err)}`
92254
+ );
92255
+ }
92256
+ }
92257
+ );
92258
+ mcp.tool(
92259
+ "fw_implement_node",
92260
+ "Replace a stub node (declare function) with a real function skeleton, or write a provided implementation directly. Preserves existing JSDoc annotations.",
92261
+ {
92262
+ filePath: external_exports.string().describe("Path to the workflow file"),
92263
+ nodeName: external_exports.string().describe("Function name of the stub node to implement"),
92264
+ implementation: external_exports.string().optional().describe("Full function body to write. If omitted, generates a skeleton."),
92265
+ workflowName: external_exports.string().optional().describe("Specific workflow name")
92266
+ },
92267
+ async (args) => {
92268
+ try {
92269
+ const filePath = path31.resolve(args.filePath);
92270
+ if (!fs28.existsSync(filePath)) {
92271
+ return makeErrorResult("FILE_NOT_FOUND", `File not found: ${args.filePath}`);
92272
+ }
92273
+ const parseResult = await parseWorkflow(filePath, { workflowName: args.workflowName });
92274
+ if (parseResult.errors.length > 0) {
92275
+ return makeErrorResult("PARSE_ERROR", `Parse errors:
92276
+ ${parseResult.errors.join("\n")}`);
92277
+ }
92278
+ const ast = parseResult.ast;
92279
+ const stubNt = ast.nodeTypes.find(
92280
+ (nt) => nt.variant === "STUB" && (nt.functionName === args.nodeName || nt.name === args.nodeName)
92281
+ );
92282
+ if (!stubNt) {
92283
+ const existing = ast.nodeTypes.find(
92284
+ (nt) => nt.functionName === args.nodeName || nt.name === args.nodeName
92285
+ );
92286
+ if (existing) {
92287
+ return makeErrorResult("ALREADY_IMPLEMENTED", `Node "${args.nodeName}" is already implemented.`);
92288
+ }
92289
+ const stubs = ast.nodeTypes.filter((nt) => nt.variant === "STUB").map((nt) => nt.functionName);
92290
+ return makeErrorResult(
92291
+ "NODE_NOT_FOUND",
92292
+ `Stub "${args.nodeName}" not found. Available stubs: ${stubs.join(", ") || "none"}`
92293
+ );
92294
+ }
92295
+ const source = fs28.readFileSync(filePath, "utf8");
92296
+ const found = findDeclareFunction(source, stubNt.functionName);
92297
+ if (!found) {
92298
+ return makeErrorResult(
92299
+ "SOURCE_MISMATCH",
92300
+ `Could not find "declare function ${stubNt.functionName}" in source file.`
92301
+ );
92302
+ }
92303
+ let replacement;
92304
+ if (args.implementation) {
92305
+ replacement = args.implementation.split("\n").map((line) => found.indent + line).join("\n");
92306
+ } else {
92307
+ const implementedType = { ...stubNt, variant: "FUNCTION" };
92308
+ const signatureLines = generateFunctionSignature(implementedType);
92309
+ replacement = signatureLines.map((line) => found.indent + line).join("\n");
92310
+ }
92311
+ const updated = source.replace(found.match, replacement);
92312
+ fs28.writeFileSync(filePath, updated, "utf8");
92313
+ return makeToolResult({
92314
+ nodeName: stubNt.functionName,
92315
+ filePath,
92316
+ action: args.implementation ? "implemented" : "scaffolded"
92317
+ });
92318
+ } catch (err) {
92319
+ return makeErrorResult(
92320
+ "IMPLEMENT_ERROR",
92321
+ `fw_implement_node failed: ${err instanceof Error ? err.message : String(err)}`
92322
+ );
92323
+ }
92324
+ }
92325
+ );
92326
+ }
92327
+ function mapTypeToTS(dataType) {
92328
+ const upper = dataType.toUpperCase();
92329
+ switch (upper) {
92330
+ case "STRING":
92331
+ return "string";
92332
+ case "NUMBER":
92333
+ return "number";
92334
+ case "BOOLEAN":
92335
+ return "boolean";
92336
+ case "OBJECT":
92337
+ return "Record<string, unknown>";
92338
+ case "ARRAY":
92339
+ return "unknown[]";
92340
+ default:
92341
+ return "unknown";
92342
+ }
92343
+ }
92344
+ function escapeRegex2(str2) {
92345
+ return str2.replace(/[.*+?^${}()|[\]\\]/g, "\\$&");
92346
+ }
92347
+
91976
92348
  // src/mcp/resources.ts
91977
92349
  function registerResources(mcp, connection, buffer) {
91978
92350
  mcp.resource(
@@ -92076,6 +92448,7 @@ async function startMcpServer(options) {
92076
92448
  registerMarketplaceTools(mcp);
92077
92449
  registerDiagramTools(mcp);
92078
92450
  registerDocsTools(mcp);
92451
+ registerModelTools(mcp);
92079
92452
  registerResources(mcp, connection, buffer);
92080
92453
  if (!options._testDeps && options.stdio) {
92081
92454
  const transport = new StdioServerTransport();
@@ -92107,20 +92480,20 @@ async function sendCommand(serverUrl, action, params) {
92107
92480
  transports: ["websocket", "polling"]
92108
92481
  });
92109
92482
  try {
92110
- await new Promise((resolve28, reject2) => {
92111
- socket.on("connect", () => resolve28());
92483
+ await new Promise((resolve31, reject2) => {
92484
+ socket.on("connect", () => resolve31());
92112
92485
  socket.on("connect_error", (err) => reject2(err));
92113
92486
  setTimeout(() => reject2(new Error("Connection timeout")), ACK_TIMEOUT);
92114
92487
  });
92115
92488
  const requestId = `${Date.now()}-${Math.random().toString(36).slice(2, 8)}`;
92116
- const result = await new Promise((resolve28) => {
92489
+ const result = await new Promise((resolve31) => {
92117
92490
  const timeout = setTimeout(() => {
92118
- resolve28({ requestId, success: false, error: "Timeout" });
92491
+ resolve31({ requestId, success: false, error: "Timeout" });
92119
92492
  }, ACK_TIMEOUT);
92120
92493
  socket.on("fw:ack", (data) => {
92121
92494
  if (data.requestId === requestId) {
92122
92495
  clearTimeout(timeout);
92123
- resolve28(data);
92496
+ resolve31(data);
92124
92497
  }
92125
92498
  });
92126
92499
  socket.emit("integration:command", { requestId, action, params });
@@ -92150,20 +92523,20 @@ async function sendBatch(serverUrl, commands) {
92150
92523
  transports: ["websocket", "polling"]
92151
92524
  });
92152
92525
  try {
92153
- await new Promise((resolve28, reject2) => {
92154
- socket.on("connect", () => resolve28());
92526
+ await new Promise((resolve31, reject2) => {
92527
+ socket.on("connect", () => resolve31());
92155
92528
  socket.on("connect_error", (err) => reject2(err));
92156
92529
  setTimeout(() => reject2(new Error("Connection timeout")), ACK_TIMEOUT);
92157
92530
  });
92158
92531
  const requestId = `${Date.now()}-${Math.random().toString(36).slice(2, 8)}`;
92159
- const result = await new Promise((resolve28) => {
92532
+ const result = await new Promise((resolve31) => {
92160
92533
  const timeout = setTimeout(() => {
92161
- resolve28({ requestId, success: false, error: "Timeout" });
92534
+ resolve31({ requestId, success: false, error: "Timeout" });
92162
92535
  }, ACK_TIMEOUT);
92163
92536
  socket.on("fw:ack", (data) => {
92164
92537
  if (data.requestId === requestId) {
92165
92538
  clearTimeout(timeout);
92166
- resolve28(data);
92539
+ resolve31(data);
92167
92540
  }
92168
92541
  });
92169
92542
  socket.emit("integration:batch", { requestId, commands });
@@ -92217,7 +92590,7 @@ async function uiBatch(json2, options) {
92217
92590
  }
92218
92591
 
92219
92592
  // src/cli/commands/grammar.ts
92220
- import * as fs28 from "fs";
92593
+ import * as fs29 from "fs";
92221
92594
  async function grammarCommand(options = {}) {
92222
92595
  const { format = "html", output } = options;
92223
92596
  try {
@@ -92236,7 +92609,7 @@ async function grammarCommand(options = {}) {
92236
92609
  content = generateGrammarDiagrams();
92237
92610
  }
92238
92611
  if (output) {
92239
- fs28.writeFileSync(output, content, "utf-8");
92612
+ fs29.writeFileSync(output, content, "utf-8");
92240
92613
  logger.success(`Grammar written to ${output}`);
92241
92614
  } else {
92242
92615
  process.stdout.write(content);
@@ -92248,12 +92621,12 @@ async function grammarCommand(options = {}) {
92248
92621
  }
92249
92622
 
92250
92623
  // src/cli/commands/run.ts
92251
- import * as path31 from "path";
92252
- import * as fs29 from "fs";
92624
+ import * as path32 from "path";
92625
+ import * as fs30 from "fs";
92253
92626
  import * as readline9 from "readline";
92254
92627
  async function runCommand(input, options) {
92255
- const filePath = path31.resolve(input);
92256
- if (!fs29.existsSync(filePath)) {
92628
+ const filePath = path32.resolve(input);
92629
+ if (!fs30.existsSync(filePath)) {
92257
92630
  throw new Error(`File not found: ${filePath}`);
92258
92631
  }
92259
92632
  let params = {};
@@ -92264,12 +92637,12 @@ async function runCommand(input, options) {
92264
92637
  throw new Error(`Invalid JSON in --params: ${options.params}`);
92265
92638
  }
92266
92639
  } else if (options.paramsFile) {
92267
- const paramsFilePath = path31.resolve(options.paramsFile);
92268
- if (!fs29.existsSync(paramsFilePath)) {
92640
+ const paramsFilePath = path32.resolve(options.paramsFile);
92641
+ if (!fs30.existsSync(paramsFilePath)) {
92269
92642
  throw new Error(`Params file not found: ${paramsFilePath}`);
92270
92643
  }
92271
92644
  try {
92272
- const content = fs29.readFileSync(paramsFilePath, "utf8");
92645
+ const content = fs30.readFileSync(paramsFilePath, "utf8");
92273
92646
  params = JSON.parse(content);
92274
92647
  } catch {
92275
92648
  throw new Error(`Failed to parse params file: ${options.paramsFile}`);
@@ -92283,12 +92656,12 @@ async function runCommand(input, options) {
92283
92656
  throw new Error(`Invalid JSON in --mocks: ${options.mocks}`);
92284
92657
  }
92285
92658
  } else if (options.mocksFile) {
92286
- const mocksFilePath = path31.resolve(options.mocksFile);
92287
- if (!fs29.existsSync(mocksFilePath)) {
92659
+ const mocksFilePath = path32.resolve(options.mocksFile);
92660
+ if (!fs30.existsSync(mocksFilePath)) {
92288
92661
  throw new Error(`Mocks file not found: ${mocksFilePath}`);
92289
92662
  }
92290
92663
  try {
92291
- const content = fs29.readFileSync(mocksFilePath, "utf8");
92664
+ const content = fs30.readFileSync(mocksFilePath, "utf8");
92292
92665
  mocks = JSON.parse(content);
92293
92666
  } catch {
92294
92667
  throw new Error(`Failed to parse mocks file: ${options.mocksFile}`);
@@ -92481,7 +92854,7 @@ async function validateMockConfig(mocks, filePath, workflowName) {
92481
92854
  }
92482
92855
  }
92483
92856
  function promptForInput(question) {
92484
- return new Promise((resolve28) => {
92857
+ return new Promise((resolve31) => {
92485
92858
  const rl = readline9.createInterface({
92486
92859
  input: process.stdin,
92487
92860
  output: process.stderr
@@ -92489,18 +92862,18 @@ function promptForInput(question) {
92489
92862
  });
92490
92863
  rl.question(question, (answer) => {
92491
92864
  rl.close();
92492
- resolve28(answer.trim());
92865
+ resolve31(answer.trim());
92493
92866
  });
92494
92867
  });
92495
92868
  }
92496
92869
 
92497
92870
  // src/cli/commands/serve.ts
92498
- import * as path32 from "path";
92499
- import * as fs31 from "fs";
92871
+ import * as path33 from "path";
92872
+ import * as fs32 from "fs";
92500
92873
 
92501
92874
  // src/server/workflow-registry.ts
92502
92875
  init_esm5();
92503
- import * as fs30 from "fs";
92876
+ import * as fs31 from "fs";
92504
92877
  var WorkflowRegistry = class {
92505
92878
  constructor(workflowDir, options = {}) {
92506
92879
  this.workflowDir = workflowDir;
@@ -92535,7 +92908,7 @@ var WorkflowRegistry = class {
92535
92908
  this.endpoints.clear();
92536
92909
  for (const file of files) {
92537
92910
  try {
92538
- const content = fs30.readFileSync(file, "utf8");
92911
+ const content = fs31.readFileSync(file, "utf8");
92539
92912
  if (!content.includes("@flowWeaver")) {
92540
92913
  continue;
92541
92914
  }
@@ -92927,11 +93300,11 @@ var WebhookServer = class {
92927
93300
 
92928
93301
  // src/cli/commands/serve.ts
92929
93302
  async function serveCommand(dir, options) {
92930
- const workflowDir = path32.resolve(dir || ".");
92931
- if (!fs31.existsSync(workflowDir)) {
93303
+ const workflowDir = path33.resolve(dir || ".");
93304
+ if (!fs32.existsSync(workflowDir)) {
92932
93305
  throw new Error(`Directory not found: ${workflowDir}`);
92933
93306
  }
92934
- if (!fs31.statSync(workflowDir).isDirectory()) {
93307
+ if (!fs32.statSync(workflowDir).isDirectory()) {
92935
93308
  throw new Error(`Not a directory: ${workflowDir}`);
92936
93309
  }
92937
93310
  const port = options.port ?? 3e3;
@@ -92974,8 +93347,8 @@ async function serveCommand(dir, options) {
92974
93347
  }
92975
93348
 
92976
93349
  // src/export/index.ts
92977
- import * as path33 from "path";
92978
- import * as fs32 from "fs";
93350
+ import * as path34 from "path";
93351
+ import * as fs33 from "fs";
92979
93352
  import * as os2 from "os";
92980
93353
  import { fileURLToPath as fileURLToPath5 } from "url";
92981
93354
 
@@ -93150,12 +93523,12 @@ Outputs:
93150
93523
 
93151
93524
  // src/export/index.ts
93152
93525
  var __filename = fileURLToPath5(import.meta.url);
93153
- var __dirname2 = path33.dirname(__filename);
93526
+ var __dirname2 = path34.dirname(__filename);
93154
93527
  async function exportMultiWorkflow(options) {
93155
- const inputPath = path33.resolve(options.input);
93156
- const outputDir = path33.resolve(options.output);
93528
+ const inputPath = path34.resolve(options.input);
93529
+ const outputDir = path34.resolve(options.output);
93157
93530
  const isDryRun = options.dryRun ?? false;
93158
- if (!fs32.existsSync(inputPath)) {
93531
+ if (!fs33.existsSync(inputPath)) {
93159
93532
  throw new Error(`Input file not found: ${inputPath}`);
93160
93533
  }
93161
93534
  const parser3 = new AnnotationParser();
@@ -93173,22 +93546,22 @@ async function exportMultiWorkflow(options) {
93173
93546
  throw new Error(`None of the requested workflows found. Available: ${available}`);
93174
93547
  }
93175
93548
  }
93176
- const workDir = isDryRun ? path33.join(os2.tmpdir(), `fw-export-multi-dryrun-${Date.now()}`) : outputDir;
93177
- fs32.mkdirSync(workDir, { recursive: true });
93178
- fs32.mkdirSync(path33.join(workDir, "workflows"), { recursive: true });
93179
- fs32.mkdirSync(path33.join(workDir, "runtime"), { recursive: true });
93549
+ const workDir = isDryRun ? path34.join(os2.tmpdir(), `fw-export-multi-dryrun-${Date.now()}`) : outputDir;
93550
+ fs33.mkdirSync(workDir, { recursive: true });
93551
+ fs33.mkdirSync(path34.join(workDir, "workflows"), { recursive: true });
93552
+ fs33.mkdirSync(path34.join(workDir, "runtime"), { recursive: true });
93180
93553
  const compiledWorkflows = [];
93181
93554
  try {
93182
93555
  for (const workflow of selectedWorkflows) {
93183
- const workflowOutputPath = path33.join(workDir, "workflows", `${workflow.name}.ts`);
93184
- fs32.copyFileSync(inputPath, workflowOutputPath);
93556
+ const workflowOutputPath = path34.join(workDir, "workflows", `${workflow.name}.ts`);
93557
+ fs33.copyFileSync(inputPath, workflowOutputPath);
93185
93558
  await compileWorkflow(workflowOutputPath, {
93186
93559
  write: true,
93187
93560
  inPlace: true,
93188
93561
  parse: { workflowName: workflow.functionName },
93189
93562
  generate: { production: options.production ?? true }
93190
93563
  });
93191
- const compiledCode = fs32.readFileSync(workflowOutputPath, "utf8");
93564
+ const compiledCode = fs33.readFileSync(workflowOutputPath, "utf8");
93192
93565
  compiledWorkflows.push({
93193
93566
  name: workflow.name,
93194
93567
  functionName: workflow.functionName,
@@ -93196,24 +93569,24 @@ async function exportMultiWorkflow(options) {
93196
93569
  code: compiledCode
93197
93570
  });
93198
93571
  }
93199
- const runtimeDir = path33.join(workDir, "runtime");
93200
- const libraryRuntimeDir = path33.resolve(__dirname2, "../runtime");
93572
+ const runtimeDir = path34.join(workDir, "runtime");
93573
+ const libraryRuntimeDir = path34.resolve(__dirname2, "../runtime");
93201
93574
  const runtimeFiles = ["function-registry.ts", "parameter-resolver.ts", "builtin-functions.ts"];
93202
93575
  for (const file of runtimeFiles) {
93203
- const srcPath = path33.join(libraryRuntimeDir, file);
93204
- const destPath = path33.join(runtimeDir, file);
93205
- if (fs32.existsSync(srcPath)) {
93206
- fs32.copyFileSync(srcPath, destPath);
93576
+ const srcPath = path34.join(libraryRuntimeDir, file);
93577
+ const destPath = path34.join(runtimeDir, file);
93578
+ if (fs33.existsSync(srcPath)) {
93579
+ fs33.copyFileSync(srcPath, destPath);
93207
93580
  }
93208
93581
  }
93209
93582
  const result = generateMultiHandler(options.target, compiledWorkflows, workDir, options);
93210
93583
  if (!isDryRun) {
93211
93584
  for (const file of result.files) {
93212
- const dirPath = path33.dirname(file.path);
93213
- if (!fs32.existsSync(dirPath)) {
93214
- fs32.mkdirSync(dirPath, { recursive: true });
93585
+ const dirPath = path34.dirname(file.path);
93586
+ if (!fs33.existsSync(dirPath)) {
93587
+ fs33.mkdirSync(dirPath, { recursive: true });
93215
93588
  }
93216
- fs32.writeFileSync(file.path, file.content);
93589
+ fs33.writeFileSync(file.path, file.content);
93217
93590
  }
93218
93591
  }
93219
93592
  return {
@@ -93226,7 +93599,7 @@ async function exportMultiWorkflow(options) {
93226
93599
  } finally {
93227
93600
  if (isDryRun) {
93228
93601
  try {
93229
- fs32.rmSync(workDir, { recursive: true, force: true });
93602
+ fs33.rmSync(workDir, { recursive: true, force: true });
93230
93603
  } catch {
93231
93604
  }
93232
93605
  }
@@ -93234,28 +93607,28 @@ async function exportMultiWorkflow(options) {
93234
93607
  }
93235
93608
  function generateMultiHandler(target, workflows, outputDir, options) {
93236
93609
  const files = [];
93237
- const serviceName = path33.basename(options.input, path33.extname(options.input)) + "-service";
93610
+ const serviceName = path34.basename(options.input, path34.extname(options.input)) + "-service";
93238
93611
  const workflowImports = workflows.map((w) => `import { ${w.functionName} } from './workflows/${w.name}.js';`).join("\n");
93239
93612
  const workflowEntries = workflows.map((w) => ` '${w.name}': ${w.functionName},`).join("\n");
93240
93613
  const openApiSpec = generateMultiWorkflowOpenAPI(workflows, serviceName);
93241
93614
  switch (target) {
93242
93615
  case "lambda":
93243
93616
  files.push({
93244
- path: path33.join(outputDir, "handler.ts"),
93617
+ path: path34.join(outputDir, "handler.ts"),
93245
93618
  content: generateLambdaMultiHandler(workflowImports, workflowEntries, serviceName)
93246
93619
  });
93247
93620
  files.push({
93248
- path: path33.join(outputDir, "openapi.ts"),
93621
+ path: path34.join(outputDir, "openapi.ts"),
93249
93622
  content: `// Generated OpenAPI specification
93250
93623
  export const openApiSpec = ${JSON.stringify(openApiSpec, null, 2)};
93251
93624
  `
93252
93625
  });
93253
93626
  files.push({
93254
- path: path33.join(outputDir, "template.yaml"),
93627
+ path: path34.join(outputDir, "template.yaml"),
93255
93628
  content: generateLambdaSAMMultiTemplate(serviceName, workflows.length)
93256
93629
  });
93257
93630
  files.push({
93258
- path: path33.join(outputDir, "package.json"),
93631
+ path: path34.join(outputDir, "package.json"),
93259
93632
  content: JSON.stringify(
93260
93633
  {
93261
93634
  name: `fw-${serviceName}`,
@@ -93276,7 +93649,7 @@ export const openApiSpec = ${JSON.stringify(openApiSpec, null, 2)};
93276
93649
  )
93277
93650
  });
93278
93651
  files.push({
93279
- path: path33.join(outputDir, "tsconfig.json"),
93652
+ path: path34.join(outputDir, "tsconfig.json"),
93280
93653
  content: JSON.stringify(
93281
93654
  {
93282
93655
  compilerOptions: {
@@ -93297,17 +93670,17 @@ export const openApiSpec = ${JSON.stringify(openApiSpec, null, 2)};
93297
93670
  break;
93298
93671
  case "vercel":
93299
93672
  files.push({
93300
- path: path33.join(outputDir, "api", "[workflow].ts"),
93673
+ path: path34.join(outputDir, "api", "[workflow].ts"),
93301
93674
  content: generateVercelMultiHandler(workflowImports, workflowEntries, serviceName)
93302
93675
  });
93303
93676
  files.push({
93304
- path: path33.join(outputDir, "openapi.ts"),
93677
+ path: path34.join(outputDir, "openapi.ts"),
93305
93678
  content: `// Generated OpenAPI specification
93306
93679
  export const openApiSpec = ${JSON.stringify(openApiSpec, null, 2)};
93307
93680
  `
93308
93681
  });
93309
93682
  files.push({
93310
- path: path33.join(outputDir, "vercel.json"),
93683
+ path: path34.join(outputDir, "vercel.json"),
93311
93684
  content: JSON.stringify(
93312
93685
  {
93313
93686
  functions: {
@@ -93324,17 +93697,17 @@ export const openApiSpec = ${JSON.stringify(openApiSpec, null, 2)};
93324
93697
  break;
93325
93698
  case "cloudflare":
93326
93699
  files.push({
93327
- path: path33.join(outputDir, "index.ts"),
93700
+ path: path34.join(outputDir, "index.ts"),
93328
93701
  content: generateCloudflareMultiHandler(workflowImports, workflowEntries, serviceName)
93329
93702
  });
93330
93703
  files.push({
93331
- path: path33.join(outputDir, "openapi.ts"),
93704
+ path: path34.join(outputDir, "openapi.ts"),
93332
93705
  content: `// Generated OpenAPI specification
93333
93706
  export const openApiSpec = ${JSON.stringify(openApiSpec, null, 2)};
93334
93707
  `
93335
93708
  });
93336
93709
  files.push({
93337
- path: path33.join(outputDir, "wrangler.toml"),
93710
+ path: path34.join(outputDir, "wrangler.toml"),
93338
93711
  content: `name = "${serviceName}"
93339
93712
  main = "dist/index.js"
93340
93713
  compatibility_date = "2024-01-01"
@@ -93344,7 +93717,7 @@ command = "npm run build"
93344
93717
  `
93345
93718
  });
93346
93719
  files.push({
93347
- path: path33.join(outputDir, "package.json"),
93720
+ path: path34.join(outputDir, "package.json"),
93348
93721
  content: JSON.stringify(
93349
93722
  {
93350
93723
  name: `fw-${serviceName}`,
@@ -93366,7 +93739,7 @@ command = "npm run build"
93366
93739
  )
93367
93740
  });
93368
93741
  files.push({
93369
- path: path33.join(outputDir, "tsconfig.json"),
93742
+ path: path34.join(outputDir, "tsconfig.json"),
93370
93743
  content: JSON.stringify(
93371
93744
  {
93372
93745
  compilerOptions: {
@@ -93387,17 +93760,17 @@ command = "npm run build"
93387
93760
  break;
93388
93761
  case "inngest":
93389
93762
  files.push({
93390
- path: path33.join(outputDir, "handler.ts"),
93763
+ path: path34.join(outputDir, "handler.ts"),
93391
93764
  content: generateInngestMultiHandler(workflowImports, workflowEntries, serviceName, workflows)
93392
93765
  });
93393
93766
  files.push({
93394
- path: path33.join(outputDir, "openapi.ts"),
93767
+ path: path34.join(outputDir, "openapi.ts"),
93395
93768
  content: `// Generated OpenAPI specification
93396
93769
  export const openApiSpec = ${JSON.stringify(openApiSpec, null, 2)};
93397
93770
  `
93398
93771
  });
93399
93772
  files.push({
93400
- path: path33.join(outputDir, "package.json"),
93773
+ path: path34.join(outputDir, "package.json"),
93401
93774
  content: JSON.stringify(
93402
93775
  {
93403
93776
  name: `fw-${serviceName}`,
@@ -93423,7 +93796,7 @@ export const openApiSpec = ${JSON.stringify(openApiSpec, null, 2)};
93423
93796
  )
93424
93797
  });
93425
93798
  files.push({
93426
- path: path33.join(outputDir, "tsconfig.json"),
93799
+ path: path34.join(outputDir, "tsconfig.json"),
93427
93800
  content: JSON.stringify(
93428
93801
  {
93429
93802
  compilerOptions: {
@@ -93879,10 +94252,10 @@ async function exportWorkflow(options) {
93879
94252
  if (options.multi) {
93880
94253
  return exportMultiWorkflow(options);
93881
94254
  }
93882
- const inputPath = path33.resolve(options.input);
93883
- const outputDir = path33.resolve(options.output);
94255
+ const inputPath = path34.resolve(options.input);
94256
+ const outputDir = path34.resolve(options.output);
93884
94257
  const isDryRun = options.dryRun ?? false;
93885
- if (!fs32.existsSync(inputPath)) {
94258
+ if (!fs33.existsSync(inputPath)) {
93886
94259
  throw new Error(`Input file not found: ${inputPath}`);
93887
94260
  }
93888
94261
  const parser3 = new AnnotationParser();
@@ -93897,8 +94270,8 @@ async function exportWorkflow(options) {
93897
94270
  const available = parseResult.workflows.map((w) => w.name).join(", ");
93898
94271
  throw new Error(`Workflow "${options.workflow}" not found. Available: ${available}`);
93899
94272
  }
93900
- const workDir = isDryRun ? path33.join(os2.tmpdir(), `fw-export-dryrun-${Date.now()}`) : outputDir;
93901
- fs32.mkdirSync(workDir, { recursive: true });
94273
+ const workDir = isDryRun ? path34.join(os2.tmpdir(), `fw-export-dryrun-${Date.now()}`) : outputDir;
94274
+ fs33.mkdirSync(workDir, { recursive: true });
93902
94275
  let compiledContent;
93903
94276
  let compiledPath;
93904
94277
  try {
@@ -93908,11 +94281,11 @@ async function exportWorkflow(options) {
93908
94281
  workDir,
93909
94282
  options.production
93910
94283
  );
93911
- compiledContent = fs32.readFileSync(compiledPath, "utf8");
94284
+ compiledContent = fs33.readFileSync(compiledPath, "utf8");
93912
94285
  } finally {
93913
94286
  if (isDryRun) {
93914
94287
  try {
93915
- fs32.rmSync(workDir, { recursive: true, force: true });
94288
+ fs33.rmSync(workDir, { recursive: true, force: true });
93916
94289
  } catch {
93917
94290
  }
93918
94291
  }
@@ -93927,8 +94300,8 @@ async function exportWorkflow(options) {
93927
94300
  handler = generateHandler(options.target, compiledPath, workflow.functionName);
93928
94301
  }
93929
94302
  const handlerFileName = getHandlerFileName(options.target, workflow.name);
93930
- const handlerPath = path33.join(outputDir, handlerFileName);
93931
- const workflowOutputPath = path33.join(outputDir, "workflow.ts");
94303
+ const handlerPath = path34.join(outputDir, handlerFileName);
94304
+ const workflowOutputPath = path34.join(outputDir, "workflow.ts");
93932
94305
  const configFiles = generateConfigFiles(
93933
94306
  options.target,
93934
94307
  workflow.name,
@@ -93936,16 +94309,16 @@ async function exportWorkflow(options) {
93936
94309
  workflow.description
93937
94310
  );
93938
94311
  if (!isDryRun) {
93939
- fs32.mkdirSync(outputDir, { recursive: true });
93940
- const handlerDir = path33.dirname(handlerPath);
93941
- if (!fs32.existsSync(handlerDir)) {
93942
- fs32.mkdirSync(handlerDir, { recursive: true });
94312
+ fs33.mkdirSync(outputDir, { recursive: true });
94313
+ const handlerDir = path34.dirname(handlerPath);
94314
+ if (!fs33.existsSync(handlerDir)) {
94315
+ fs33.mkdirSync(handlerDir, { recursive: true });
93943
94316
  }
93944
- fs32.writeFileSync(handlerPath, handler);
94317
+ fs33.writeFileSync(handlerPath, handler);
93945
94318
  for (const file of configFiles) {
93946
- fs32.writeFileSync(file.path, file.content);
94319
+ fs33.writeFileSync(file.path, file.content);
93947
94320
  }
93948
- fs32.writeFileSync(workflowOutputPath, compiledContent);
94321
+ fs33.writeFileSync(workflowOutputPath, compiledContent);
93949
94322
  }
93950
94323
  const files = [
93951
94324
  { path: handlerPath, content: handler },
@@ -93960,8 +94333,8 @@ async function exportWorkflow(options) {
93960
94333
  };
93961
94334
  }
93962
94335
  async function compileToOutput(inputPath, functionName, outputDir, production) {
93963
- const outputPath = path33.join(outputDir, "workflow.ts");
93964
- fs32.copyFileSync(inputPath, outputPath);
94336
+ const outputPath = path34.join(outputDir, "workflow.ts");
94337
+ fs33.copyFileSync(inputPath, outputPath);
93965
94338
  await compileWorkflow(outputPath, {
93966
94339
  write: true,
93967
94340
  inPlace: true,
@@ -93972,7 +94345,7 @@ async function compileToOutput(inputPath, functionName, outputDir, production) {
93972
94345
  }
93973
94346
  function generateHandler(target, workflowPath, functionName) {
93974
94347
  const template = getTemplate(target);
93975
- const relativePath = target === "vercel" ? `../${path33.basename(workflowPath).replace(".ts", ".js")}` : `./${path33.basename(workflowPath).replace(".ts", ".js")}`;
94348
+ const relativePath = target === "vercel" ? `../${path34.basename(workflowPath).replace(".ts", ".js")}` : `./${path34.basename(workflowPath).replace(".ts", ".js")}`;
93976
94349
  return template.replace("{{GENERATED_HEADER}}", getGeneratedBranding().header(`export --target ${target}`)).replace("{{WORKFLOW_IMPORT}}", `import { ${functionName} } from '${relativePath}';`).replace(/\{\{FUNCTION_NAME\}\}/g, functionName).replace("{{MAX_DURATION}}", "60");
93977
94350
  }
93978
94351
  function getTemplate(target) {
@@ -94004,14 +94377,14 @@ function generateConfigFiles(target, workflowName, outputDir, description) {
94004
94377
  switch (target) {
94005
94378
  case "lambda":
94006
94379
  files.push({
94007
- path: path33.join(outputDir, "template.yaml"),
94380
+ path: path34.join(outputDir, "template.yaml"),
94008
94381
  content: SAM_TEMPLATE2.replace(/\{\{WORKFLOW_NAME\}\}/g, workflowName).replace(
94009
94382
  "{{WORKFLOW_DESCRIPTION}}",
94010
94383
  description || `Flow Weaver workflow: ${workflowName}`
94011
94384
  ).replace(/\{\{WORKFLOW_PATH\}\}/g, workflowName)
94012
94385
  });
94013
94386
  files.push({
94014
- path: path33.join(outputDir, "package.json"),
94387
+ path: path34.join(outputDir, "package.json"),
94015
94388
  content: JSON.stringify(
94016
94389
  {
94017
94390
  name: `fw-${workflowName}`,
@@ -94032,7 +94405,7 @@ function generateConfigFiles(target, workflowName, outputDir, description) {
94032
94405
  )
94033
94406
  });
94034
94407
  files.push({
94035
- path: path33.join(outputDir, "tsconfig.json"),
94408
+ path: path34.join(outputDir, "tsconfig.json"),
94036
94409
  content: JSON.stringify(
94037
94410
  {
94038
94411
  compilerOptions: {
@@ -94053,7 +94426,7 @@ function generateConfigFiles(target, workflowName, outputDir, description) {
94053
94426
  break;
94054
94427
  case "vercel":
94055
94428
  files.push({
94056
- path: path33.join(outputDir, "vercel.json"),
94429
+ path: path34.join(outputDir, "vercel.json"),
94057
94430
  content: JSON.stringify(
94058
94431
  {
94059
94432
  functions: {
@@ -94070,7 +94443,7 @@ function generateConfigFiles(target, workflowName, outputDir, description) {
94070
94443
  break;
94071
94444
  case "cloudflare":
94072
94445
  files.push({
94073
- path: path33.join(outputDir, "wrangler.toml"),
94446
+ path: path34.join(outputDir, "wrangler.toml"),
94074
94447
  content: `name = "${workflowName}"
94075
94448
  main = "dist/index.js"
94076
94449
  compatibility_date = "2024-01-01"
@@ -94080,7 +94453,7 @@ command = "npm run build"
94080
94453
  `
94081
94454
  });
94082
94455
  files.push({
94083
- path: path33.join(outputDir, "package.json"),
94456
+ path: path34.join(outputDir, "package.json"),
94084
94457
  content: JSON.stringify(
94085
94458
  {
94086
94459
  name: `fw-${workflowName}`,
@@ -94102,7 +94475,7 @@ command = "npm run build"
94102
94475
  )
94103
94476
  });
94104
94477
  files.push({
94105
- path: path33.join(outputDir, "tsconfig.json"),
94478
+ path: path34.join(outputDir, "tsconfig.json"),
94106
94479
  content: JSON.stringify(
94107
94480
  {
94108
94481
  compilerOptions: {
@@ -94123,7 +94496,7 @@ command = "npm run build"
94123
94496
  break;
94124
94497
  case "inngest":
94125
94498
  files.push({
94126
- path: path33.join(outputDir, "package.json"),
94499
+ path: path34.join(outputDir, "package.json"),
94127
94500
  content: JSON.stringify(
94128
94501
  {
94129
94502
  name: `fw-${workflowName}`,
@@ -94147,7 +94520,7 @@ command = "npm run build"
94147
94520
  )
94148
94521
  });
94149
94522
  files.push({
94150
- path: path33.join(outputDir, "tsconfig.json"),
94523
+ path: path34.join(outputDir, "tsconfig.json"),
94151
94524
  content: JSON.stringify(
94152
94525
  {
94153
94526
  compilerOptions: {
@@ -94299,14 +94672,14 @@ async function exportCommand(input, options) {
94299
94672
  }
94300
94673
 
94301
94674
  // src/cli/commands/openapi.ts
94302
- import * as path34 from "path";
94303
- import * as fs33 from "fs";
94675
+ import * as path35 from "path";
94676
+ import * as fs34 from "fs";
94304
94677
  async function openapiCommand(dir, options) {
94305
- const workflowDir = path34.resolve(dir);
94306
- if (!fs33.existsSync(workflowDir)) {
94678
+ const workflowDir = path35.resolve(dir);
94679
+ if (!fs34.existsSync(workflowDir)) {
94307
94680
  throw new Error(`Directory not found: ${workflowDir}`);
94308
94681
  }
94309
- if (!fs33.statSync(workflowDir).isDirectory()) {
94682
+ if (!fs34.statSync(workflowDir).isDirectory()) {
94310
94683
  throw new Error(`Not a directory: ${workflowDir}`);
94311
94684
  }
94312
94685
  const registry2 = new WorkflowRegistry(workflowDir);
@@ -94325,8 +94698,8 @@ async function openapiCommand(dir, options) {
94325
94698
  const format = options.format || "json";
94326
94699
  const spec = format === "yaml" ? generateOpenAPIYaml(endpoints, generatorOptions) : generateOpenAPIJson(endpoints, generatorOptions);
94327
94700
  if (options.output) {
94328
- const outputPath = path34.resolve(options.output);
94329
- fs33.writeFileSync(outputPath, spec);
94701
+ const outputPath = path35.resolve(options.output);
94702
+ fs34.writeFileSync(outputPath, spec);
94330
94703
  logger.success(`OpenAPI specification written to ${outputPath}`);
94331
94704
  } else {
94332
94705
  process.stdout.write(spec + "\n");
@@ -94334,8 +94707,8 @@ async function openapiCommand(dir, options) {
94334
94707
  }
94335
94708
 
94336
94709
  // src/cli/commands/plugin.ts
94337
- import * as fs34 from "fs";
94338
- import * as path35 from "path";
94710
+ import * as fs35 from "fs";
94711
+ import * as path36 from "path";
94339
94712
  var PLUGIN_NAME_RE = /^[a-zA-Z0-9][-a-zA-Z0-9_.]*$/;
94340
94713
  var VALID_AREAS = ["sidebar", "main", "toolbar", "modal", "panel"];
94341
94714
  function validatePluginName(name) {
@@ -94462,18 +94835,18 @@ async function pluginInitCommand(name, options) {
94462
94835
  }
94463
94836
  return;
94464
94837
  }
94465
- const targetDir = path35.resolve("plugins", name);
94838
+ const targetDir = path36.resolve("plugins", name);
94466
94839
  const filesCreated = [];
94467
94840
  const filesSkipped = [];
94468
94841
  for (const [relativePath, content] of Object.entries(files)) {
94469
- const absPath = path35.join(targetDir, relativePath);
94470
- const dir = path35.dirname(absPath);
94471
- fs34.mkdirSync(dir, { recursive: true });
94472
- if (fs34.existsSync(absPath) && !force) {
94842
+ const absPath = path36.join(targetDir, relativePath);
94843
+ const dir = path36.dirname(absPath);
94844
+ fs35.mkdirSync(dir, { recursive: true });
94845
+ if (fs35.existsSync(absPath) && !force) {
94473
94846
  filesSkipped.push(relativePath);
94474
94847
  continue;
94475
94848
  }
94476
- fs34.writeFileSync(absPath, content, "utf8");
94849
+ fs35.writeFileSync(absPath, content, "utf8");
94477
94850
  filesCreated.push(relativePath);
94478
94851
  }
94479
94852
  logger.section("Plugin scaffolded");
@@ -94492,8 +94865,8 @@ async function pluginInitCommand(name, options) {
94492
94865
 
94493
94866
  // src/cli/commands/migrate.ts
94494
94867
  init_esm5();
94495
- import * as fs35 from "fs";
94496
- import * as path36 from "path";
94868
+ import * as fs36 from "fs";
94869
+ import * as path37 from "path";
94497
94870
  async function migrateCommand(globPattern, options = {}) {
94498
94871
  const { dryRun = false, diff = false } = options;
94499
94872
  const files = globSync(globPattern, { ignore: ["**/node_modules/**", "**/*.generated.ts"] });
@@ -94509,9 +94882,9 @@ async function migrateCommand(globPattern, options = {}) {
94509
94882
  let skippedCount = 0;
94510
94883
  let errorCount = 0;
94511
94884
  for (const file of files) {
94512
- const filePath = path36.resolve(file);
94885
+ const filePath = path37.resolve(file);
94513
94886
  try {
94514
- const sourceCode = fs35.readFileSync(filePath, "utf8");
94887
+ const sourceCode = fs36.readFileSync(filePath, "utf8");
94515
94888
  const parseResult = await parseWorkflow(filePath);
94516
94889
  if (parseResult.errors.length > 0) {
94517
94890
  logger.error(` ${file}: parse errors \u2014 skipping`);
@@ -94544,7 +94917,7 @@ ${file}:`);
94544
94917
  migratedCount++;
94545
94918
  continue;
94546
94919
  }
94547
- fs35.writeFileSync(filePath, genResult.code, "utf8");
94920
+ fs36.writeFileSync(filePath, genResult.code, "utf8");
94548
94921
  logger.success(` ${file}: migrated`);
94549
94922
  migratedCount++;
94550
94923
  } catch (error2) {
@@ -94676,21 +95049,21 @@ async function changelogCommand(options = {}) {
94676
95049
 
94677
95050
  // src/cli/commands/strip.ts
94678
95051
  init_esm5();
94679
- import * as fs36 from "fs";
94680
- import * as path37 from "path";
95052
+ import * as fs37 from "fs";
95053
+ import * as path38 from "path";
94681
95054
  async function stripCommand(input, options = {}) {
94682
95055
  const { output, dryRun = false, verbose = false } = options;
94683
95056
  let pattern = input;
94684
95057
  try {
94685
- if (fs36.existsSync(input) && fs36.statSync(input).isDirectory()) {
94686
- pattern = path37.join(input, "**/*.ts");
95058
+ if (fs37.existsSync(input) && fs37.statSync(input).isDirectory()) {
95059
+ pattern = path38.join(input, "**/*.ts");
94687
95060
  }
94688
95061
  } catch {
94689
95062
  }
94690
95063
  const allFiles = await glob(pattern, { absolute: true });
94691
95064
  const files = allFiles.filter((f) => {
94692
95065
  try {
94693
- return fs36.statSync(f).isFile();
95066
+ return fs37.statSync(f).isFile();
94694
95067
  } catch {
94695
95068
  return false;
94696
95069
  }
@@ -94702,28 +95075,28 @@ async function stripCommand(input, options = {}) {
94702
95075
  let stripped = 0;
94703
95076
  let skipped = 0;
94704
95077
  for (const filePath of files) {
94705
- const content = fs36.readFileSync(filePath, "utf-8");
95078
+ const content = fs37.readFileSync(filePath, "utf-8");
94706
95079
  if (!hasInPlaceMarkers(content)) {
94707
95080
  skipped++;
94708
95081
  if (verbose) {
94709
- logger.info(`Skipped (no markers): ${path37.relative(process.cwd(), filePath)}`);
95082
+ logger.info(`Skipped (no markers): ${path38.relative(process.cwd(), filePath)}`);
94710
95083
  }
94711
95084
  continue;
94712
95085
  }
94713
95086
  const result = stripGeneratedSections(content);
94714
95087
  if (dryRun) {
94715
- logger.info(`Would strip: ${path37.relative(process.cwd(), filePath)}`);
95088
+ logger.info(`Would strip: ${path38.relative(process.cwd(), filePath)}`);
94716
95089
  stripped++;
94717
95090
  continue;
94718
95091
  }
94719
- const outPath = output ? path37.join(path37.resolve(output), path37.basename(filePath)) : filePath;
95092
+ const outPath = output ? path38.join(path38.resolve(output), path38.basename(filePath)) : filePath;
94720
95093
  if (output) {
94721
- fs36.mkdirSync(path37.dirname(outPath), { recursive: true });
95094
+ fs37.mkdirSync(path38.dirname(outPath), { recursive: true });
94722
95095
  }
94723
- fs36.writeFileSync(outPath, result);
95096
+ fs37.writeFileSync(outPath, result);
94724
95097
  stripped++;
94725
95098
  if (verbose) {
94726
- logger.success(`Stripped: ${path37.relative(process.cwd(), outPath)}`);
95099
+ logger.success(`Stripped: ${path38.relative(process.cwd(), outPath)}`);
94727
95100
  }
94728
95101
  }
94729
95102
  logger.success(`${stripped} file${stripped !== 1 ? "s" : ""} stripped, ${skipped} skipped`);
@@ -94802,9 +95175,188 @@ async function docsSearchCommand(query, options) {
94802
95175
  logger.newline();
94803
95176
  }
94804
95177
 
95178
+ // src/cli/commands/status.ts
95179
+ import * as fs38 from "fs";
95180
+ import * as path39 from "path";
95181
+ init_validator();
95182
+ function formatPortList(ports) {
95183
+ return Object.entries(ports).filter(([name]) => name !== "execute" && name !== "onSuccess" && name !== "onFailure").map(([name, port]) => `${name}(${port.dataType.toLowerCase()})`);
95184
+ }
95185
+ async function statusCommand(input, options = {}) {
95186
+ const { workflowName, json: json2 = false } = options;
95187
+ try {
95188
+ const filePath = path39.resolve(input);
95189
+ if (!fs38.existsSync(filePath)) {
95190
+ if (json2) {
95191
+ console.log(JSON.stringify({ error: `File not found: ${input}` }));
95192
+ } else {
95193
+ logger.error(`File not found: ${input}`);
95194
+ }
95195
+ process.exit(1);
95196
+ }
95197
+ const parseResult = await parseWorkflow(filePath, { workflowName });
95198
+ if (parseResult.errors.length > 0) {
95199
+ if (json2) {
95200
+ console.log(JSON.stringify({ error: `Parse errors: ${parseResult.errors.join(", ")}` }));
95201
+ } else {
95202
+ logger.error("Parse errors:");
95203
+ parseResult.errors.forEach((e) => logger.error(` ${e}`));
95204
+ }
95205
+ process.exit(1);
95206
+ }
95207
+ const ast = parseResult.ast;
95208
+ const instanceTypeMap = /* @__PURE__ */ new Map();
95209
+ for (const nt of ast.nodeTypes) {
95210
+ instanceTypeMap.set(nt.name, nt);
95211
+ if (nt.functionName !== nt.name) {
95212
+ instanceTypeMap.set(nt.functionName, nt);
95213
+ }
95214
+ }
95215
+ const nodes = [];
95216
+ const seen = /* @__PURE__ */ new Set();
95217
+ for (const instance of ast.instances) {
95218
+ const nt = instanceTypeMap.get(instance.nodeType);
95219
+ if (!nt || seen.has(nt.functionName)) continue;
95220
+ seen.add(nt.functionName);
95221
+ nodes.push({
95222
+ name: nt.functionName,
95223
+ status: nt.variant === "STUB" ? "STUB" : "OK",
95224
+ inputs: formatPortList(nt.inputs),
95225
+ outputs: formatPortList(nt.outputs)
95226
+ });
95227
+ }
95228
+ const implemented = nodes.filter((n) => n.status === "OK").length;
95229
+ const total = nodes.length;
95230
+ const validation = validator.validate(ast, { mode: "draft" });
95231
+ const structuralErrors = validation.errors.filter((e) => e.code !== "STUB_NODE").map((e) => e.message);
95232
+ const result = {
95233
+ name: ast.name,
95234
+ implemented,
95235
+ total,
95236
+ nodes,
95237
+ structurallyValid: structuralErrors.length === 0,
95238
+ structuralErrors
95239
+ };
95240
+ if (json2) {
95241
+ console.log(JSON.stringify(result, null, 2));
95242
+ } else {
95243
+ logger.section(`${ast.name}: ${implemented}/${total} nodes implemented`);
95244
+ logger.newline();
95245
+ const maxNameLen = Math.max(...nodes.map((n) => n.name.length), 0);
95246
+ for (const node of nodes) {
95247
+ const tag = node.status === "STUB" ? "[STUB]" : "[OK] ";
95248
+ const paddedName = node.name.padEnd(maxNameLen);
95249
+ const inputStr = node.inputs.length > 0 ? `inputs: ${node.inputs.join(", ")}` : "";
95250
+ const outputStr = node.outputs.length > 0 ? `outputs: ${node.outputs.join(", ")}` : "";
95251
+ const arrow = inputStr && outputStr ? " \u2192 " : "";
95252
+ const portsStr = `${inputStr}${arrow}${outputStr}`;
95253
+ if (node.status === "STUB") {
95254
+ logger.warn(` ${paddedName} ${tag} ${portsStr}`);
95255
+ } else {
95256
+ logger.success(` ${paddedName} ${tag} ${portsStr}`);
95257
+ }
95258
+ }
95259
+ if (structuralErrors.length > 0) {
95260
+ logger.newline();
95261
+ logger.error(`Structural errors (${structuralErrors.length}):`);
95262
+ structuralErrors.forEach((e) => logger.error(` - ${e}`));
95263
+ } else {
95264
+ logger.newline();
95265
+ logger.success("Graph structure is valid.");
95266
+ }
95267
+ }
95268
+ } catch (error2) {
95269
+ if (json2) {
95270
+ console.log(JSON.stringify({ error: getErrorMessage(error2) }));
95271
+ } else {
95272
+ logger.error(`Status failed: ${getErrorMessage(error2)}`);
95273
+ }
95274
+ process.exit(1);
95275
+ }
95276
+ }
95277
+
95278
+ // src/cli/commands/implement.ts
95279
+ import * as fs39 from "fs";
95280
+ import * as path40 from "path";
95281
+ function findDeclareFunction2(source, functionName) {
95282
+ const lines = source.split("\n");
95283
+ const escaped = functionName.replace(/[.*+?^${}()|[\]\\]/g, "\\$&");
95284
+ const startPattern = new RegExp(`^(\\s*)declare\\s+function\\s+${escaped}\\s*\\(`);
95285
+ for (let i = 0; i < lines.length; i++) {
95286
+ const m = lines[i].match(startPattern);
95287
+ if (!m) continue;
95288
+ const indent = m[1] || "";
95289
+ let accumulated = lines[i];
95290
+ let j = i;
95291
+ while (!accumulated.trimEnd().endsWith(";") && j < lines.length - 1) {
95292
+ j++;
95293
+ accumulated += "\n" + lines[j];
95294
+ }
95295
+ return { match: accumulated, indent };
95296
+ }
95297
+ return null;
95298
+ }
95299
+ async function implementCommand(input, nodeName, options = {}) {
95300
+ const { workflowName, preview = false } = options;
95301
+ try {
95302
+ const filePath = path40.resolve(input);
95303
+ if (!fs39.existsSync(filePath)) {
95304
+ logger.error(`File not found: ${input}`);
95305
+ process.exit(1);
95306
+ }
95307
+ const parseResult = await parseWorkflow(filePath, { workflowName });
95308
+ if (parseResult.errors.length > 0) {
95309
+ logger.error("Parse errors:");
95310
+ parseResult.errors.forEach((e) => logger.error(` ${e}`));
95311
+ process.exit(1);
95312
+ }
95313
+ const ast = parseResult.ast;
95314
+ const stubNodeType = ast.nodeTypes.find(
95315
+ (nt) => nt.variant === "STUB" && (nt.functionName === nodeName || nt.name === nodeName)
95316
+ );
95317
+ if (!stubNodeType) {
95318
+ const existingNt = ast.nodeTypes.find(
95319
+ (nt) => nt.functionName === nodeName || nt.name === nodeName
95320
+ );
95321
+ if (existingNt) {
95322
+ logger.warn(`Node "${nodeName}" is already implemented.`);
95323
+ process.exit(0);
95324
+ }
95325
+ const available = ast.nodeTypes.filter((nt) => nt.variant === "STUB").map((nt) => nt.functionName);
95326
+ if (available.length === 0) {
95327
+ logger.error("No stub nodes found in this workflow.");
95328
+ } else {
95329
+ logger.error(`Stub node "${nodeName}" not found. Available stubs: ${available.join(", ")}`);
95330
+ }
95331
+ process.exit(1);
95332
+ }
95333
+ const source = fs39.readFileSync(filePath, "utf8");
95334
+ const found = findDeclareFunction2(source, stubNodeType.functionName);
95335
+ if (!found) {
95336
+ logger.error(`Could not find "declare function ${stubNodeType.functionName}" in source file.`);
95337
+ process.exit(1);
95338
+ }
95339
+ const implementedType = { ...stubNodeType, variant: "FUNCTION" };
95340
+ const signatureLines = generateFunctionSignature(implementedType);
95341
+ const replacement = signatureLines.map((line) => found.indent + line).join("\n");
95342
+ if (preview) {
95343
+ logger.section(`Preview: ${stubNodeType.functionName}`);
95344
+ logger.newline();
95345
+ console.log(replacement);
95346
+ } else {
95347
+ const updated = source.replace(found.match, replacement);
95348
+ fs39.writeFileSync(filePath, updated, "utf8");
95349
+ logger.success(`Implemented ${stubNodeType.functionName} in ${path40.basename(filePath)}`);
95350
+ }
95351
+ } catch (error2) {
95352
+ logger.error(`Implement failed: ${getErrorMessage(error2)}`);
95353
+ process.exit(1);
95354
+ }
95355
+ }
95356
+
94805
95357
  // src/cli/commands/market.ts
94806
- import * as fs37 from "fs";
94807
- import * as path38 from "path";
95358
+ import * as fs40 from "fs";
95359
+ import * as path41 from "path";
94808
95360
  import { execSync as execSync6 } from "child_process";
94809
95361
  async function marketInitCommand(name, options = {}) {
94810
95362
  if (!name.startsWith("flowweaver-pack-")) {
@@ -94812,11 +95364,11 @@ async function marketInitCommand(name, options = {}) {
94812
95364
  logger.warn(`Name should follow "flowweaver-pack-*" convention, using "${suggested}"`);
94813
95365
  name = suggested;
94814
95366
  }
94815
- const targetDir = path38.resolve(name);
94816
- if (fs37.existsSync(targetDir)) {
94817
- const stat = fs37.statSync(targetDir);
95367
+ const targetDir = path41.resolve(name);
95368
+ if (fs40.existsSync(targetDir)) {
95369
+ const stat = fs40.statSync(targetDir);
94818
95370
  if (stat.isDirectory()) {
94819
- const contents = fs37.readdirSync(targetDir);
95371
+ const contents = fs40.readdirSync(targetDir);
94820
95372
  if (contents.length > 0) {
94821
95373
  logger.error(`Directory "${name}" already exists and is not empty`);
94822
95374
  process.exit(1);
@@ -94831,13 +95383,13 @@ async function marketInitCommand(name, options = {}) {
94831
95383
  logger.newline();
94832
95384
  const dirs = [
94833
95385
  targetDir,
94834
- path38.join(targetDir, "src"),
94835
- path38.join(targetDir, "src", "node-types"),
94836
- path38.join(targetDir, "src", "workflows"),
94837
- path38.join(targetDir, "src", "patterns")
95386
+ path41.join(targetDir, "src"),
95387
+ path41.join(targetDir, "src", "node-types"),
95388
+ path41.join(targetDir, "src", "workflows"),
95389
+ path41.join(targetDir, "src", "patterns")
94838
95390
  ];
94839
95391
  for (const dir of dirs) {
94840
- fs37.mkdirSync(dir, { recursive: true });
95392
+ fs40.mkdirSync(dir, { recursive: true });
94841
95393
  }
94842
95394
  const shortName = name.replace(/^flowweaver-pack-/, "");
94843
95395
  const pkg = {
@@ -94868,8 +95420,8 @@ async function marketInitCommand(name, options = {}) {
94868
95420
  },
94869
95421
  files: ["dist", "flowweaver.manifest.json", "README.md", "LICENSE"]
94870
95422
  };
94871
- fs37.writeFileSync(
94872
- path38.join(targetDir, "package.json"),
95423
+ fs40.writeFileSync(
95424
+ path41.join(targetDir, "package.json"),
94873
95425
  JSON.stringify(pkg, null, 2) + "\n"
94874
95426
  );
94875
95427
  const tsconfig = {
@@ -94887,8 +95439,8 @@ async function marketInitCommand(name, options = {}) {
94887
95439
  include: ["src"],
94888
95440
  exclude: ["node_modules", "dist"]
94889
95441
  };
94890
- fs37.writeFileSync(
94891
- path38.join(targetDir, "tsconfig.json"),
95442
+ fs40.writeFileSync(
95443
+ path41.join(targetDir, "tsconfig.json"),
94892
95444
  JSON.stringify(tsconfig, null, 2) + "\n"
94893
95445
  );
94894
95446
  const sampleNodeType = `/**
@@ -94906,21 +95458,21 @@ export function sample(execute: () => void, data: string): { result: string } {
94906
95458
  return { result: data.toUpperCase() };
94907
95459
  }
94908
95460
  `;
94909
- fs37.writeFileSync(path38.join(targetDir, "src", "node-types", "sample.ts"), sampleNodeType);
94910
- fs37.writeFileSync(
94911
- path38.join(targetDir, "src", "node-types", "index.ts"),
95461
+ fs40.writeFileSync(path41.join(targetDir, "src", "node-types", "sample.ts"), sampleNodeType);
95462
+ fs40.writeFileSync(
95463
+ path41.join(targetDir, "src", "node-types", "index.ts"),
94912
95464
  "export { sample } from './sample.js';\n"
94913
95465
  );
94914
- fs37.writeFileSync(
94915
- path38.join(targetDir, "src", "workflows", "index.ts"),
95466
+ fs40.writeFileSync(
95467
+ path41.join(targetDir, "src", "workflows", "index.ts"),
94916
95468
  "// Export workflows here\n"
94917
95469
  );
94918
- fs37.writeFileSync(
94919
- path38.join(targetDir, "src", "patterns", "index.ts"),
95470
+ fs40.writeFileSync(
95471
+ path41.join(targetDir, "src", "patterns", "index.ts"),
94920
95472
  "// Export patterns here\n"
94921
95473
  );
94922
- fs37.writeFileSync(
94923
- path38.join(targetDir, "src", "index.ts"),
95474
+ fs40.writeFileSync(
95475
+ path41.join(targetDir, "src", "index.ts"),
94924
95476
  [
94925
95477
  "export * from './node-types/index.js';",
94926
95478
  "export * from './workflows/index.js';",
@@ -94953,9 +95505,9 @@ npm run pack # Generate flowweaver.manifest.json
94953
95505
  npm publish # Publish to npm
94954
95506
  \`\`\`
94955
95507
  `;
94956
- fs37.writeFileSync(path38.join(targetDir, "README.md"), readme);
94957
- fs37.writeFileSync(
94958
- path38.join(targetDir, ".gitignore"),
95508
+ fs40.writeFileSync(path41.join(targetDir, "README.md"), readme);
95509
+ fs40.writeFileSync(
95510
+ path41.join(targetDir, ".gitignore"),
94959
95511
  ["node_modules", "dist", "*.tgz", ""].join("\n")
94960
95512
  );
94961
95513
  logger.success("Created package.json");
@@ -94975,7 +95527,7 @@ npm publish # Publish to npm
94975
95527
  logger.newline();
94976
95528
  }
94977
95529
  async function marketPackCommand(directory, options = {}) {
94978
- const dir = path38.resolve(directory ?? ".");
95530
+ const dir = path41.resolve(directory ?? ".");
94979
95531
  const { json: json2 = false, verbose = false } = options;
94980
95532
  if (!json2) {
94981
95533
  logger.section("Packing Marketplace Package");
@@ -95014,21 +95566,21 @@ async function marketPackCommand(directory, options = {}) {
95014
95566
  }
95015
95567
  const outPath = writeManifest(dir, manifest);
95016
95568
  logger.newline();
95017
- logger.success(`Manifest written to ${path38.relative(dir, outPath)}`);
95569
+ logger.success(`Manifest written to ${path41.relative(dir, outPath)}`);
95018
95570
  if (warnings.length > 0) {
95019
95571
  logger.warn(`${warnings.length} warning(s) \u2014 consider fixing before publishing`);
95020
95572
  }
95021
95573
  logger.newline();
95022
95574
  }
95023
95575
  async function marketPublishCommand(directory, options = {}) {
95024
- const dir = path38.resolve(directory ?? ".");
95576
+ const dir = path41.resolve(directory ?? ".");
95025
95577
  const { dryRun = false, tag } = options;
95026
95578
  logger.section("Publishing Marketplace Package");
95027
95579
  await marketPackCommand(dir, { json: false });
95028
- if (!fs37.existsSync(path38.join(dir, "LICENSE"))) {
95580
+ if (!fs40.existsSync(path41.join(dir, "LICENSE"))) {
95029
95581
  logger.warn("LICENSE file not found \u2014 consider adding one");
95030
95582
  }
95031
- const pkg = JSON.parse(fs37.readFileSync(path38.join(dir, "package.json"), "utf-8"));
95583
+ const pkg = JSON.parse(fs40.readFileSync(path41.join(dir, "package.json"), "utf-8"));
95032
95584
  logger.info(`Publishing ${pkg.name}@${pkg.version}`);
95033
95585
  const npmArgs = ["publish"];
95034
95586
  if (dryRun) npmArgs.push("--dry-run");
@@ -95063,7 +95615,7 @@ async function marketInstallCommand(packageSpec, options = {}) {
95063
95615
  process.exit(1);
95064
95616
  }
95065
95617
  const packageName = resolvePackageName2(packageSpec);
95066
- const manifest = readManifest(path38.join(process.cwd(), "node_modules", packageName));
95618
+ const manifest = readManifest(path41.join(process.cwd(), "node_modules", packageName));
95067
95619
  if (json2) {
95068
95620
  console.log(JSON.stringify({
95069
95621
  success: true,
@@ -95147,7 +95699,7 @@ async function marketListCommand(options = {}) {
95147
95699
  }
95148
95700
  function resolvePackageName2(spec) {
95149
95701
  if (spec.endsWith(".tgz") || spec.endsWith(".tar.gz")) {
95150
- const base = path38.basename(spec, spec.endsWith(".tar.gz") ? ".tar.gz" : ".tgz");
95702
+ const base = path41.basename(spec, spec.endsWith(".tar.gz") ? ".tar.gz" : ".tgz");
95151
95703
  const match2 = base.match(/^(.+)-\d+\.\d+\.\d+/);
95152
95704
  return match2 ? match2[1] : base;
95153
95705
  }
@@ -95196,7 +95748,7 @@ function displayInstalledPackage(pkg) {
95196
95748
  }
95197
95749
 
95198
95750
  // src/cli/index.ts
95199
- var version2 = true ? "0.8.3" : "0.0.0-dev";
95751
+ var version2 = true ? "0.9.1" : "0.0.0-dev";
95200
95752
  var program2 = new Command();
95201
95753
  program2.name("flow-weaver").description("Flow Weaver Annotations - Compile and validate workflow files").version(version2, "-v, --version", "Output the current version");
95202
95754
  program2.configureOutput({
@@ -95465,6 +96017,22 @@ program2.command("migrate <glob>").description("Migrate workflow files to curren
95465
96017
  process.exit(1);
95466
96018
  }
95467
96019
  });
96020
+ program2.command("status <input>").description("Report implementation progress for stub workflows").option("-w, --workflow-name <name>", "Specific workflow name").option("--json", "Output as JSON", false).action(async (input, options) => {
96021
+ try {
96022
+ await statusCommand(input, options);
96023
+ } catch (error2) {
96024
+ logger.error(`Command failed: ${getErrorMessage(error2)}`);
96025
+ process.exit(1);
96026
+ }
96027
+ });
96028
+ program2.command("implement <input> <node>").description("Replace a stub node with a real function skeleton").option("-w, --workflow-name <name>", "Specific workflow name").option("-p, --preview", "Preview the generated code without writing", false).action(async (input, node, options) => {
96029
+ try {
96030
+ await implementCommand(input, node, options);
96031
+ } catch (error2) {
96032
+ logger.error(`Command failed: ${getErrorMessage(error2)}`);
96033
+ process.exit(1);
96034
+ }
96035
+ });
95468
96036
  program2.command("changelog").description("Generate changelog from git history, categorized by file path").option("--last-tag", "From last git tag to HEAD", false).option("--since <date>", 'Date-based range (e.g., "2024-01-01")').option("-r, --range <range>", 'Custom git range (e.g., "v0.1.0..HEAD")').action(async (options) => {
95469
96037
  try {
95470
96038
  await changelogCommand(options);