@synergenius/flow-weaver 0.19.2 → 0.19.4

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.
@@ -9671,7 +9671,7 @@ var VERSION;
9671
9671
  var init_generated_version = __esm({
9672
9672
  "src/generated-version.ts"() {
9673
9673
  "use strict";
9674
- VERSION = "0.19.2";
9674
+ VERSION = "0.19.4";
9675
9675
  }
9676
9676
  });
9677
9677
 
@@ -16272,7 +16272,7 @@ ${file}:${line}:${column}: ERROR: ${pluginText}${e.text}`;
16272
16272
  return result;
16273
16273
  }
16274
16274
  var fs53 = __require("fs");
16275
- var os3 = __require("os");
16275
+ var os4 = __require("os");
16276
16276
  var path56 = __require("path");
16277
16277
  var ESBUILD_BINARY_PATH = process.env.ESBUILD_BINARY_PATH || ESBUILD_BINARY_PATH;
16278
16278
  var isValidBinaryPath = (x) => !!x && x !== "/usr/bin/esbuild";
@@ -16314,7 +16314,7 @@ ${file}:${line}:${column}: ERROR: ${pluginText}${e.text}`;
16314
16314
  let pkg;
16315
16315
  let subpath;
16316
16316
  let isWASM = false;
16317
- let platformKey = `${process.platform} ${os3.arch()} ${os3.endianness()}`;
16317
+ let platformKey = `${process.platform} ${os4.arch()} ${os4.endianness()}`;
16318
16318
  if (platformKey in knownWindowsPackages) {
16319
16319
  pkg = knownWindowsPackages[platformKey];
16320
16320
  subpath = "esbuild.exe";
@@ -35842,7 +35842,17 @@ var init_parser2 = __esm({
35842
35842
  const hasExtension = extensions.some((ext2) => moduleSpecifier.endsWith(ext2));
35843
35843
  if (hasExtension) {
35844
35844
  const fullPath = path6.resolve(currentDir, moduleSpecifier);
35845
- return fs7.existsSync(fullPath) ? fullPath : null;
35845
+ if (fs7.existsSync(fullPath)) return fullPath;
35846
+ if (moduleSpecifier.endsWith(".js")) {
35847
+ const tsPath = fullPath.replace(/\.js$/, ".ts");
35848
+ if (fs7.existsSync(tsPath)) return tsPath;
35849
+ const tsxPath = fullPath.replace(/\.js$/, ".tsx");
35850
+ if (fs7.existsSync(tsxPath)) return tsxPath;
35851
+ } else if (moduleSpecifier.endsWith(".jsx")) {
35852
+ const tsxPath = fullPath.replace(/\.jsx$/, ".tsx");
35853
+ if (fs7.existsSync(tsxPath)) return tsxPath;
35854
+ }
35855
+ return null;
35846
35856
  }
35847
35857
  for (const ext2 of extensions) {
35848
35858
  const fullPath = path6.resolve(currentDir, moduleSpecifier + ext2);
@@ -56773,7 +56783,7 @@ var require_has_flag = __commonJS({
56773
56783
  var require_supports_color = __commonJS({
56774
56784
  "node_modules/supports-color/index.js"(exports2, module2) {
56775
56785
  "use strict";
56776
- var os3 = __require("os");
56786
+ var os4 = __require("os");
56777
56787
  var tty = __require("tty");
56778
56788
  var hasFlag = require_has_flag();
56779
56789
  var { env } = process;
@@ -56821,7 +56831,7 @@ var require_supports_color = __commonJS({
56821
56831
  return min;
56822
56832
  }
56823
56833
  if (process.platform === "win32") {
56824
- const osRelease = os3.release().split(".");
56834
+ const osRelease = os4.release().split(".");
56825
56835
  if (Number(osRelease[0]) >= 10 && Number(osRelease[2]) >= 10586) {
56826
56836
  return Number(osRelease[2]) >= 14931 ? 3 : 2;
56827
56837
  }
@@ -84187,7 +84197,7 @@ function resolvePath(workspaceRoot, studioPath) {
84187
84197
  }
84188
84198
  return resolved2;
84189
84199
  }
84190
- let normalized = studioPath;
84200
+ let normalized = studioPath.replace(/\\/g, "/");
84191
84201
  if (normalized.startsWith("/cloud")) {
84192
84202
  normalized = normalized.slice("/cloud".length);
84193
84203
  }
@@ -84206,7 +84216,7 @@ function toVirtualPath(workspaceRoot, realPath) {
84206
84216
  if (rel.startsWith("..")) {
84207
84217
  return "/" + path23.basename(realPath);
84208
84218
  }
84209
- return "/" + rel;
84219
+ return "/" + rel.replace(/\\/g, "/");
84210
84220
  }
84211
84221
 
84212
84222
  // src/cli/tunnel/handlers/file-ops.ts
@@ -85077,7 +85087,9 @@ var executionHandlers = {
85077
85087
  };
85078
85088
 
85079
85089
  // src/cli/tunnel/handlers/stubs.ts
85090
+ import * as os2 from "node:os";
85080
85091
  var stub = (value2) => () => Promise.resolve(value2);
85092
+ var lazyStub = (fn) => () => Promise.resolve(fn());
85081
85093
  var stubHandlers = {
85082
85094
  // --- Completions / Quick Info ---
85083
85095
  getCompletions: stub([]),
@@ -85112,8 +85124,8 @@ var stubHandlers = {
85112
85124
  exportNodeTypes: stub({ success: true }),
85113
85125
  exportBundle: stub({ success: true }),
85114
85126
  // --- Misc ---
85115
- getUserDataPath: stub("/tmp"),
85116
- getTempDirectory: stub("/tmp"),
85127
+ getUserDataPath: lazyStub(() => os2.tmpdir()),
85128
+ getTempDirectory: lazyStub(() => os2.tmpdir()),
85117
85129
  openDirectoryInExplorer: stub({ success: true }),
85118
85130
  checkDeployPrerequisites: stub({ success: true }),
85119
85131
  appendToLog: stub(void 0),
@@ -100150,10 +100162,10 @@ function registerQueryTools(mcp) {
100150
100162
  async (args) => {
100151
100163
  try {
100152
100164
  const filePath = path30.resolve(args.filePath);
100153
- const parseResult = await parseWorkflow(filePath, { workflowName: args.workflowName });
100165
+ const parseResult = await parseWorkflow(filePath, { workflowName: args.workflowName, projectDir: path30.dirname(filePath) });
100154
100166
  if (parseResult.errors.length > 0 && parseResult.errors.some((e) => typeof e === "string" && e.includes("No workflows found"))) {
100155
100167
  try {
100156
- const ntResult = await parseWorkflow(filePath, { nodeTypesOnly: true });
100168
+ const ntResult = await parseWorkflow(filePath, { nodeTypesOnly: true, projectDir: path30.dirname(filePath) });
100157
100169
  if (ntResult.errors.length === 0 && ntResult.ast.nodeTypes?.length > 0) {
100158
100170
  return makeToolResult({
100159
100171
  nodeTypesOnly: true,
@@ -100199,10 +100211,10 @@ ${parseResult.errors.join("\n")}`
100199
100211
  async (args) => {
100200
100212
  try {
100201
100213
  const filePath = path30.resolve(args.filePath);
100202
- const parseResult = await parseWorkflow(filePath, { workflowName: args.workflowName });
100214
+ const parseResult = await parseWorkflow(filePath, { workflowName: args.workflowName, projectDir: path30.dirname(filePath) });
100203
100215
  if (parseResult.errors.length > 0 && parseResult.errors.some((e) => typeof e === "string" && e.includes("No workflows found"))) {
100204
100216
  try {
100205
- const ntResult = await parseWorkflow(filePath, { nodeTypesOnly: true });
100217
+ const ntResult = await parseWorkflow(filePath, { nodeTypesOnly: true, projectDir: path30.dirname(filePath) });
100206
100218
  if (ntResult.errors.length === 0 && ntResult.ast.nodeTypes?.length > 0) {
100207
100219
  const count = ntResult.ast.nodeTypes.length;
100208
100220
  return makeToolResult({
@@ -100358,9 +100370,11 @@ ${parseResult.errors.join("\n")}`);
100358
100370
  },
100359
100371
  async (args) => {
100360
100372
  try {
100373
+ const file1 = path30.resolve(args.file1);
100374
+ const file2 = path30.resolve(args.file2);
100361
100375
  const [result1, result2] = await Promise.all([
100362
- parseWorkflow(path30.resolve(args.file1), { workflowName: args.workflowName }),
100363
- parseWorkflow(path30.resolve(args.file2), { workflowName: args.workflowName })
100376
+ parseWorkflow(file1, { workflowName: args.workflowName, projectDir: path30.dirname(file1) }),
100377
+ parseWorkflow(file2, { workflowName: args.workflowName, projectDir: path30.dirname(file2) })
100364
100378
  ]);
100365
100379
  if (result1.errors.length > 0) {
100366
100380
  return makeErrorResult(
@@ -100423,10 +100437,10 @@ Query types:
100423
100437
  async (args) => {
100424
100438
  try {
100425
100439
  const filePath = path30.resolve(args.filePath);
100426
- let parseResult = await parseWorkflow(filePath, { workflowName: args.workflowName });
100440
+ let parseResult = await parseWorkflow(filePath, { workflowName: args.workflowName, projectDir: path30.dirname(filePath) });
100427
100441
  if (parseResult.errors.length > 0 && args.query === "node-types" && parseResult.errors.some((e) => typeof e === "string" && e.includes("No workflows found"))) {
100428
100442
  try {
100429
- const ntResult = await parseWorkflow(filePath, { nodeTypesOnly: true });
100443
+ const ntResult = await parseWorkflow(filePath, { nodeTypesOnly: true, projectDir: path30.dirname(filePath) });
100430
100444
  if (ntResult.errors.length === 0) {
100431
100445
  parseResult = ntResult;
100432
100446
  }
@@ -101533,7 +101547,7 @@ function registerExportTools(mcp) {
101533
101547
  }
101534
101548
  let parseResult;
101535
101549
  try {
101536
- parseResult = await parseWorkflow(filePath, { nodeTypesOnly: false });
101550
+ parseResult = await parseWorkflow(filePath, { nodeTypesOnly: false, projectDir: path37.dirname(filePath) });
101537
101551
  } catch (err) {
101538
101552
  return makeErrorResult(
101539
101553
  "PARSE_ERROR",
@@ -101542,7 +101556,7 @@ function registerExportTools(mcp) {
101542
101556
  }
101543
101557
  if (parseResult.errors.length > 0) {
101544
101558
  try {
101545
- const ntResult = await parseWorkflow(filePath, { nodeTypesOnly: true });
101559
+ const ntResult = await parseWorkflow(filePath, { nodeTypesOnly: true, projectDir: path37.dirname(filePath) });
101546
101560
  if (ntResult.errors.length === 0) {
101547
101561
  parseResult = ntResult;
101548
101562
  }
@@ -104958,7 +104972,7 @@ init_compile();
104958
104972
  init_parser2();
104959
104973
  import * as path47 from "path";
104960
104974
  import * as fs44 from "fs";
104961
- import * as os2 from "os";
104975
+ import * as os3 from "os";
104962
104976
  async function exportWorkflow(options) {
104963
104977
  const { createTargetRegistry: createTargetRegistry2 } = await Promise.resolve().then(() => (init_deployment(), deployment_exports));
104964
104978
  const registry2 = await createTargetRegistry2(process.cwd());
@@ -105024,7 +105038,7 @@ async function exportSingleWorkflowViaRegistry(target, inputPath, outputDir, isD
105024
105038
  );
105025
105039
  let compiledContent;
105026
105040
  if (needsCompiledWorkflow) {
105027
- const workDir = isDryRun ? path47.join(os2.tmpdir(), `fw-export-dryrun-${Date.now()}`) : outputDir;
105041
+ const workDir = isDryRun ? path47.join(os3.tmpdir(), `fw-export-dryrun-${Date.now()}`) : outputDir;
105028
105042
  fs44.mkdirSync(workDir, { recursive: true });
105029
105043
  try {
105030
105044
  const compiledPath = await compileToOutput(
@@ -106425,7 +106439,7 @@ function displayInstalledPackage(pkg) {
106425
106439
  // src/cli/index.ts
106426
106440
  init_logger();
106427
106441
  init_error_utils();
106428
- var version2 = true ? "0.19.2" : "0.0.0-dev";
106442
+ var version2 = true ? "0.19.4" : "0.0.0-dev";
106429
106443
  var program2 = new Command();
106430
106444
  program2.name("flow-weaver").description("Flow Weaver Annotations - Compile and validate workflow files").option("-v, --version", "Output the current version").option("--no-color", "Disable colors").option("--color", "Force colors").on("option:version", () => {
106431
106445
  logger.banner(version2);
@@ -2,7 +2,9 @@
2
2
  * Stub handlers — methods that return sensible defaults.
3
3
  * Matches the no-op return values from flow-weaver-platform/src/routes/studio-rpc.ts.
4
4
  */
5
+ import * as os from 'node:os';
5
6
  const stub = (value) => () => Promise.resolve(value);
7
+ const lazyStub = (fn) => () => Promise.resolve(fn());
6
8
  export const stubHandlers = {
7
9
  // --- Completions / Quick Info ---
8
10
  getCompletions: stub([]),
@@ -37,8 +39,8 @@ export const stubHandlers = {
37
39
  exportNodeTypes: stub({ success: true }),
38
40
  exportBundle: stub({ success: true }),
39
41
  // --- Misc ---
40
- getUserDataPath: stub('/tmp'),
41
- getTempDirectory: stub('/tmp'),
42
+ getUserDataPath: lazyStub(() => os.tmpdir()),
43
+ getTempDirectory: lazyStub(() => os.tmpdir()),
42
44
  openDirectoryInExplorer: stub({ success: true }),
43
45
  checkDeployPrerequisites: stub({ success: true }),
44
46
  appendToLog: stub(undefined),
@@ -22,8 +22,9 @@ export function resolvePath(workspaceRoot, studioPath) {
22
22
  }
23
23
  return resolved;
24
24
  }
25
+ // Normalize backslashes to forward slashes (Windows clients may send them)
26
+ let normalized = studioPath.replace(/\\/g, '/');
25
27
  // Strip /cloud prefix if present
26
- let normalized = studioPath;
27
28
  if (normalized.startsWith('/cloud')) {
28
29
  normalized = normalized.slice('/cloud'.length);
29
30
  }
@@ -47,6 +48,7 @@ export function toVirtualPath(workspaceRoot, realPath) {
47
48
  if (rel.startsWith('..')) {
48
49
  return '/' + path.basename(realPath);
49
50
  }
50
- return '/' + rel;
51
+ // Always use forward slashes in virtual paths (Windows path.relative uses backslashes)
52
+ return '/' + rel.replace(/\\/g, '/');
51
53
  }
52
54
  //# sourceMappingURL=path-resolver.js.map
@@ -1,2 +1,2 @@
1
- export declare const VERSION = "0.19.2";
1
+ export declare const VERSION = "0.19.4";
2
2
  //# sourceMappingURL=generated-version.d.ts.map
@@ -1,3 +1,3 @@
1
1
  // Auto-generated by scripts/generate-version.ts — do not edit manually
2
- export const VERSION = '0.19.2';
2
+ export const VERSION = '0.19.4';
3
3
  //# sourceMappingURL=generated-version.js.map
package/dist/generator.js CHANGED
@@ -1,4 +1,5 @@
1
1
  /* eslint-disable no-console */
2
+ import * as path from 'node:path';
2
3
  import { parseWorkflow } from "./api/parse.js";
3
4
  import { validateWorkflow } from "./api/validate.js";
4
5
  import { generateCode } from "./api/generate.js";
@@ -36,7 +37,7 @@ export class WorkflowGenerator {
36
37
  */
37
38
  async parseWithLogging(filePath, workflowName) {
38
39
  console.log("Parsing annotations...");
39
- const parseResult = await parseWorkflow(filePath, { workflowName });
40
+ const parseResult = await parseWorkflow(filePath, { workflowName, projectDir: path.dirname(filePath) });
40
41
  if (parseResult.errors.length > 0) {
41
42
  console.error(`\\n❌ ${parseResult.errors.length} parse error(s):`);
42
43
  parseResult.errors.forEach((error) => {
@@ -66,7 +66,7 @@ export function registerExportTools(mcp) {
66
66
  // 3. Parse the file to discover workflows and node types
67
67
  let parseResult;
68
68
  try {
69
- parseResult = await parseWorkflow(filePath, { nodeTypesOnly: false });
69
+ parseResult = await parseWorkflow(filePath, { nodeTypesOnly: false, projectDir: path.dirname(filePath) });
70
70
  }
71
71
  catch (err) {
72
72
  return makeErrorResult('PARSE_ERROR', `Failed to parse ${filePath}: ${err instanceof Error ? err.message : String(err)}`);
@@ -74,7 +74,7 @@ export function registerExportTools(mcp) {
74
74
  if (parseResult.errors.length > 0) {
75
75
  // Try node-types-only parse
76
76
  try {
77
- const ntResult = await parseWorkflow(filePath, { nodeTypesOnly: true });
77
+ const ntResult = await parseWorkflow(filePath, { nodeTypesOnly: true, projectDir: path.dirname(filePath) });
78
78
  if (ntResult.errors.length === 0) {
79
79
  parseResult = ntResult;
80
80
  }
@@ -29,12 +29,12 @@ export function registerQueryTools(mcp) {
29
29
  }, async (args) => {
30
30
  try {
31
31
  const filePath = path.resolve(args.filePath);
32
- const parseResult = await parseWorkflow(filePath, { workflowName: args.workflowName });
32
+ const parseResult = await parseWorkflow(filePath, { workflowName: args.workflowName, projectDir: path.dirname(filePath) });
33
33
  // If no workflows found, try node-type-only mode
34
34
  if (parseResult.errors.length > 0 &&
35
35
  parseResult.errors.some((e) => typeof e === 'string' && e.includes('No workflows found'))) {
36
36
  try {
37
- const ntResult = await parseWorkflow(filePath, { nodeTypesOnly: true });
37
+ const ntResult = await parseWorkflow(filePath, { nodeTypesOnly: true, projectDir: path.dirname(filePath) });
38
38
  if (ntResult.errors.length === 0 && ntResult.ast.nodeTypes?.length > 0) {
39
39
  return makeToolResult({
40
40
  nodeTypesOnly: true,
@@ -69,12 +69,12 @@ export function registerQueryTools(mcp) {
69
69
  }, async (args) => {
70
70
  try {
71
71
  const filePath = path.resolve(args.filePath);
72
- const parseResult = await parseWorkflow(filePath, { workflowName: args.workflowName });
72
+ const parseResult = await parseWorkflow(filePath, { workflowName: args.workflowName, projectDir: path.dirname(filePath) });
73
73
  // If no workflows found, try node-type-only mode
74
74
  if (parseResult.errors.length > 0 &&
75
75
  parseResult.errors.some((e) => typeof e === 'string' && e.includes('No workflows found'))) {
76
76
  try {
77
- const ntResult = await parseWorkflow(filePath, { nodeTypesOnly: true });
77
+ const ntResult = await parseWorkflow(filePath, { nodeTypesOnly: true, projectDir: path.dirname(filePath) });
78
78
  if (ntResult.errors.length === 0 && ntResult.ast.nodeTypes?.length > 0) {
79
79
  const count = ntResult.ast.nodeTypes.length;
80
80
  return makeToolResult({
@@ -230,9 +230,11 @@ export function registerQueryTools(mcp) {
230
230
  workflowName: z.string().optional().describe('Specific workflow name'),
231
231
  }, async (args) => {
232
232
  try {
233
+ const file1 = path.resolve(args.file1);
234
+ const file2 = path.resolve(args.file2);
233
235
  const [result1, result2] = await Promise.all([
234
- parseWorkflow(path.resolve(args.file1), { workflowName: args.workflowName }),
235
- parseWorkflow(path.resolve(args.file2), { workflowName: args.workflowName }),
236
+ parseWorkflow(file1, { workflowName: args.workflowName, projectDir: path.dirname(file1) }),
237
+ parseWorkflow(file2, { workflowName: args.workflowName, projectDir: path.dirname(file2) }),
236
238
  ]);
237
239
  if (result1.errors.length > 0) {
238
240
  return makeErrorResult(parseErrorCode(result1.errors), `Parse errors in file1:\n${result1.errors.join('\n')}`);
@@ -273,13 +275,13 @@ export function registerQueryTools(mcp) {
273
275
  }, async (args) => {
274
276
  try {
275
277
  const filePath = path.resolve(args.filePath);
276
- let parseResult = await parseWorkflow(filePath, { workflowName: args.workflowName });
278
+ let parseResult = await parseWorkflow(filePath, { workflowName: args.workflowName, projectDir: path.dirname(filePath) });
277
279
  // For node-types query, fall back to nodeTypesOnly mode if no workflows found
278
280
  if (parseResult.errors.length > 0 &&
279
281
  args.query === 'node-types' &&
280
282
  parseResult.errors.some((e) => typeof e === 'string' && e.includes('No workflows found'))) {
281
283
  try {
282
- const ntResult = await parseWorkflow(filePath, { nodeTypesOnly: true });
284
+ const ntResult = await parseWorkflow(filePath, { nodeTypesOnly: true, projectDir: path.dirname(filePath) });
283
285
  if (ntResult.errors.length === 0) {
284
286
  parseResult = ntResult;
285
287
  }
package/dist/parser.js CHANGED
@@ -311,11 +311,28 @@ export class AnnotationParser {
311
311
  }
312
312
  resolveModulePath(moduleSpecifier, currentDir) {
313
313
  const extensions = ['.ts', '.tsx', '.js', '.jsx'];
314
- // If already has extension, check if exists
314
+ // If already has extension, check if exists (with ESM .js → .ts fallback)
315
315
  const hasExtension = extensions.some((ext) => moduleSpecifier.endsWith(ext));
316
316
  if (hasExtension) {
317
317
  const fullPath = path.resolve(currentDir, moduleSpecifier);
318
- return fs.existsSync(fullPath) ? fullPath : null;
318
+ if (fs.existsSync(fullPath))
319
+ return fullPath;
320
+ // ESM convention: TypeScript files use .js extensions in imports.
321
+ // If the .js file doesn't exist, try the .ts/.tsx equivalent.
322
+ if (moduleSpecifier.endsWith('.js')) {
323
+ const tsPath = fullPath.replace(/\.js$/, '.ts');
324
+ if (fs.existsSync(tsPath))
325
+ return tsPath;
326
+ const tsxPath = fullPath.replace(/\.js$/, '.tsx');
327
+ if (fs.existsSync(tsxPath))
328
+ return tsxPath;
329
+ }
330
+ else if (moduleSpecifier.endsWith('.jsx')) {
331
+ const tsxPath = fullPath.replace(/\.jsx$/, '.tsx');
332
+ if (fs.existsSync(tsxPath))
333
+ return tsxPath;
334
+ }
335
+ return null;
319
336
  }
320
337
  // Try each extension in order
321
338
  for (const ext of extensions) {
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@synergenius/flow-weaver",
3
- "version": "0.19.2",
3
+ "version": "0.19.4",
4
4
  "description": "Deterministic workflow compiler for AI agents. Compiles to standalone TypeScript, no runtime dependencies.",
5
5
  "private": false,
6
6
  "type": "module",