depwire-cli 0.9.27 → 0.9.28

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.
@@ -16,7 +16,7 @@ import {
16
16
  parseTypeScriptFile,
17
17
  scanSecurity,
18
18
  searchSymbols
19
- } from "./chunk-DA5LWNJ4.js";
19
+ } from "./chunk-ITEGMPF7.js";
20
20
 
21
21
  // src/viz/data.ts
22
22
  import { basename } from "path";
@@ -45,12 +45,18 @@ function prepareVizData(graph, projectRoot) {
45
45
  if (!arc.edgeKinds.includes(edge.kind)) {
46
46
  arc.edgeKinds.push(edge.kind);
47
47
  }
48
+ if (edge.crossLanguage) {
49
+ arc.crossLanguage = true;
50
+ arc.edgeType = edge.edgeType || arc.edgeType;
51
+ }
48
52
  } else {
49
53
  arcMap.set(key, {
50
54
  sourceFile: edge.sourceFile,
51
55
  targetFile: edge.targetFile,
52
56
  edgeCount: 1,
53
- edgeKinds: [edge.kind]
57
+ edgeKinds: [edge.kind],
58
+ crossLanguage: edge.crossLanguage || false,
59
+ edgeType: edge.edgeType
54
60
  });
55
61
  }
56
62
  }
@@ -238,7 +244,7 @@ Depwire visualization running at ${url2}`);
238
244
  console.error(`File changed: ${filePath} \u2014 re-parsing project...`);
239
245
  try {
240
246
  const parsedFiles = await parseProject(projectRoot, options);
241
- const newGraph = buildGraph(parsedFiles);
247
+ const newGraph = buildGraph(parsedFiles, projectRoot);
242
248
  graph.clear();
243
249
  newGraph.forEachNode((node, attrs) => {
244
250
  graph.addNode(node, attrs);
@@ -257,7 +263,7 @@ Depwire visualization running at ${url2}`);
257
263
  console.error(`File added: ${filePath} \u2014 re-parsing project...`);
258
264
  try {
259
265
  const parsedFiles = await parseProject(projectRoot, options);
260
- const newGraph = buildGraph(parsedFiles);
266
+ const newGraph = buildGraph(parsedFiles, projectRoot);
261
267
  graph.clear();
262
268
  newGraph.forEachNode((node, attrs) => {
263
269
  graph.addNode(node, attrs);
@@ -276,7 +282,7 @@ Depwire visualization running at ${url2}`);
276
282
  console.error(`File deleted: ${filePath} \u2014 re-parsing project...`);
277
283
  try {
278
284
  const parsedFiles = await parseProject(projectRoot, options);
279
- const newGraph = buildGraph(parsedFiles);
285
+ const newGraph = buildGraph(parsedFiles, projectRoot);
280
286
  graph.clear();
281
287
  newGraph.forEachNode((node, attrs) => {
282
288
  graph.addNode(node, attrs);
@@ -509,7 +515,7 @@ async function connectToRepo(source, subdirectory, state) {
509
515
  message: `No supported source files (.ts, .tsx, .js, .jsx, .py, .go) found in ${projectRoot}`
510
516
  };
511
517
  }
512
- const graph = buildGraph(parsedFiles);
518
+ const graph = buildGraph(parsedFiles, projectRoot);
513
519
  state.graph = graph;
514
520
  state.projectRoot = projectRoot;
515
521
  state.projectName = projectName;
@@ -939,7 +945,7 @@ function getToolsList() {
939
945
  },
940
946
  {
941
947
  name: "impact_analysis",
942
- description: "Analyze what would break if a symbol is changed, renamed, or removed. Shows direct dependents, transitive dependents (chain reaction), and all affected files. Pass a symbol name (e.g., 'Router') or a fully qualified ID (e.g., 'src/router.ts::Router') for exact matching. If multiple symbols share the same name, returns all matches for disambiguation. Use this before making changes to understand the blast radius.",
948
+ description: "Analyze what would break if a symbol is changed, renamed, or removed. Shows direct dependents, transitive dependents (chain reaction), and all affected files. Cross-language edges included \u2014 a TypeScript fetch call to a Python route will show the Python file as affected. Pass a symbol name (e.g., 'Router') or a fully qualified ID (e.g., 'src/router.ts::Router') for exact matching. If multiple symbols share the same name, returns all matches for disambiguation. Use this before making changes to understand the blast radius.",
943
949
  inputSchema: {
944
950
  type: "object",
945
951
  properties: {
@@ -957,7 +963,7 @@ function getToolsList() {
957
963
  },
958
964
  {
959
965
  name: "get_file_context",
960
- description: "Get complete context about a file \u2014 all symbols defined in it, all imports, all exports, and all files that import from it.",
966
+ description: "Get complete context about a file \u2014 all symbols defined in it, all imports, all exports, and all files that import from it. Includes cross-language connections (REST API calls, subprocess invocations).",
961
967
  inputSchema: {
962
968
  type: "object",
963
969
  properties: {
@@ -1094,7 +1100,7 @@ function getToolsList() {
1094
1100
  },
1095
1101
  {
1096
1102
  name: "simulate_change",
1097
- description: `Simulate an architectural change before touching any code. Returns health score delta, broken imports, and affected nodes. Zero file I/O \u2014 pure in-memory simulation.
1103
+ description: `Simulate an architectural change before touching any code. Returns health score delta, broken imports, and affected nodes. Zero file I/O \u2014 pure in-memory simulation. Cross-language edges included \u2014 deleting a Python route file will show TypeScript callers as affected.
1098
1104
 
1099
1105
  Operations:
1100
1106
  - delete: Simulate deleting a file. Shows every file that would break and the full blast radius.
@@ -1777,7 +1783,7 @@ async function handleUpdateProjectDocs(docType, state) {
1777
1783
  const docsDir = join5(state.projectRoot, ".depwire");
1778
1784
  console.error("Regenerating project documentation...");
1779
1785
  const parsedFiles = await parseProject(state.projectRoot);
1780
- const graph = buildGraph(parsedFiles);
1786
+ const graph = buildGraph(parsedFiles, state.projectRoot);
1781
1787
  const parseTime = (Date.now() - startTime) / 1e3;
1782
1788
  state.graph = graph;
1783
1789
  const packageJsonPath = join5(__dirname, "../../package.json");
package/dist/index.js CHANGED
@@ -17,7 +17,7 @@ import {
17
17
  stashChanges,
18
18
  updateFileInGraph,
19
19
  watchProject
20
- } from "./chunk-RGD3YJYQ.js";
20
+ } from "./chunk-VJLBOFCD.js";
21
21
  import {
22
22
  SimulationEngine,
23
23
  analyzeDeadCode,
@@ -31,7 +31,7 @@ import {
31
31
  parseProject,
32
32
  scanSecurity,
33
33
  searchSymbols
34
- } from "./chunk-DA5LWNJ4.js";
34
+ } from "./chunk-ITEGMPF7.js";
35
35
 
36
36
  // src/index.ts
37
37
  import { Command } from "commander";
@@ -410,7 +410,7 @@ async function runTemporalAnalysis(projectDir, options) {
410
410
  }
411
411
  await checkoutCommit(projectDir, commit.hash);
412
412
  const parsedFiles = await parseProject(projectDir);
413
- const graph = buildGraph(parsedFiles);
413
+ const graph = buildGraph(parsedFiles, projectDir);
414
414
  const projectGraph = exportToJSON(graph, projectDir);
415
415
  const snapshot = createSnapshot(
416
416
  projectGraph,
@@ -758,7 +758,7 @@ async function whatif(dir, options) {
758
758
  const projectRoot2 = dir === "." ? findProjectRoot() : resolve2(dir);
759
759
  console.error(`Parsing project: ${projectRoot2}`);
760
760
  const parsedFiles2 = await parseProject(projectRoot2);
761
- const graph2 = buildGraph(parsedFiles2);
761
+ const graph2 = buildGraph(parsedFiles2, projectRoot2);
762
762
  console.error(`Built graph: ${graph2.order} symbols, ${graph2.size} edges`);
763
763
  const vizData = prepareVizData(graph2, projectRoot2);
764
764
  const emptyResult = {
@@ -784,7 +784,7 @@ async function whatif(dir, options) {
784
784
  const projectRoot = dir === "." ? findProjectRoot() : resolve2(dir);
785
785
  console.error(`Parsing project: ${projectRoot}`);
786
786
  const parsedFiles = await parseProject(projectRoot);
787
- const graph = buildGraph(parsedFiles);
787
+ const graph = buildGraph(parsedFiles, projectRoot);
788
788
  console.error(`Built graph: ${graph.order} symbols, ${graph.size} edges`);
789
789
  console.error("");
790
790
  const engine = new SimulationEngine(graph);
@@ -1039,7 +1039,7 @@ async function securityCommand(dir, options) {
1039
1039
  const startTime = Date.now();
1040
1040
  const parsedFiles = await parseProject(projectRoot);
1041
1041
  console.error(`Parsed ${parsedFiles.length} files`);
1042
- const graph = buildGraph(parsedFiles);
1042
+ const graph = buildGraph(parsedFiles, projectRoot);
1043
1043
  console.error(`Built graph: ${graph.order} symbols, ${graph.size} edges`);
1044
1044
  const result = await scanSecurity(projectRoot, graph, {
1045
1045
  target: options.target,
@@ -1089,7 +1089,7 @@ program.command("parse").description("Parse a TypeScript project and build depen
1089
1089
  verbose: options.verbose
1090
1090
  });
1091
1091
  console.log(`Parsed ${parsedFiles.length} files`);
1092
- const graph = buildGraph(parsedFiles);
1092
+ const graph = buildGraph(parsedFiles, projectRoot);
1093
1093
  const projectGraph = exportToJSON(graph, projectRoot);
1094
1094
  const json = options.pretty ? JSON.stringify(projectGraph, null, 2) : JSON.stringify(projectGraph);
1095
1095
  writeFileSync(options.output, json, "utf-8");
@@ -1131,7 +1131,7 @@ program.command("query").description("Query impact analysis for a symbol").argum
1131
1131
  } else {
1132
1132
  console.log("Parsing project...");
1133
1133
  const parsedFiles = await parseProject(projectRoot);
1134
- graph = buildGraph(parsedFiles);
1134
+ graph = buildGraph(parsedFiles, projectRoot);
1135
1135
  }
1136
1136
  const matches = searchSymbols(graph, symbolName);
1137
1137
  if (matches.length === 0) {
@@ -1177,7 +1177,7 @@ program.command("viz").description("Launch interactive arc diagram visualization
1177
1177
  verbose: options.verbose
1178
1178
  });
1179
1179
  console.log(`Parsed ${parsedFiles.length} files`);
1180
- const graph = buildGraph(parsedFiles);
1180
+ const graph = buildGraph(parsedFiles, projectRoot);
1181
1181
  const vizData = prepareVizData(graph, projectRoot);
1182
1182
  console.log(`Found ${vizData.stats.totalSymbols} symbols, ${vizData.stats.totalCrossFileEdges} cross-file edges`);
1183
1183
  const port = parseInt(options.port, 10);
@@ -1225,7 +1225,7 @@ program.command("mcp").description("Start MCP server for AI coding tools").argum
1225
1225
  console.error(`Parsing project: ${projectRootToConnect}`);
1226
1226
  const parsedFiles = await parseProject(projectRootToConnect);
1227
1227
  console.error(`Parsed ${parsedFiles.length} files`);
1228
- const graph = buildGraph(parsedFiles);
1228
+ const graph = buildGraph(parsedFiles, projectRootToConnect);
1229
1229
  console.error(`Built graph: ${graph.order} symbols, ${graph.size} edges`);
1230
1230
  state.graph = graph;
1231
1231
  state.projectRoot = projectRootToConnect;
@@ -1292,7 +1292,7 @@ program.command("docs").description("Generate comprehensive codebase documentati
1292
1292
  verbose: options.verbose
1293
1293
  });
1294
1294
  console.log(`Parsed ${parsedFiles.length} files`);
1295
- const graph = buildGraph(parsedFiles);
1295
+ const graph = buildGraph(parsedFiles, projectRoot);
1296
1296
  const parseTime = (Date.now() - startTime) / 1e3;
1297
1297
  console.log(`Built graph: ${graph.order} symbols, ${graph.size} edges`);
1298
1298
  if (options.verbose) {
@@ -1374,7 +1374,7 @@ program.command("health").description("Analyze dependency architecture health (0
1374
1374
  const projectRoot = directory ? resolve4(directory) : findProjectRoot();
1375
1375
  const startTime = Date.now();
1376
1376
  const parsedFiles = await parseProject(projectRoot);
1377
- const graph = buildGraph(parsedFiles);
1377
+ const graph = buildGraph(parsedFiles, projectRoot);
1378
1378
  const parseTime = Date.now() - startTime;
1379
1379
  const report = calculateHealthScore(graph, projectRoot);
1380
1380
  const trend = getHealthTrend(projectRoot, report.overall);
@@ -1398,7 +1398,7 @@ program.command("dead-code").description("Identify dead code - symbols defined b
1398
1398
  const projectRoot = directory ? resolve4(directory) : findProjectRoot();
1399
1399
  const startTime = Date.now();
1400
1400
  const parsedFiles = await parseProject(projectRoot);
1401
- const graph = buildGraph(parsedFiles);
1401
+ const graph = buildGraph(parsedFiles, projectRoot);
1402
1402
  const confidence = options.includeLow ? "low" : options.confidence || "medium";
1403
1403
  const report = analyzeDeadCode(graph, projectRoot, {
1404
1404
  confidence,
@@ -4,11 +4,11 @@ import {
4
4
  startMcpServer,
5
5
  updateFileInGraph,
6
6
  watchProject
7
- } from "./chunk-RGD3YJYQ.js";
7
+ } from "./chunk-VJLBOFCD.js";
8
8
  import {
9
9
  buildGraph,
10
10
  parseProject
11
- } from "./chunk-DA5LWNJ4.js";
11
+ } from "./chunk-ITEGMPF7.js";
12
12
 
13
13
  // src/mcpb-entry.ts
14
14
  import { resolve } from "path";
@@ -21,7 +21,7 @@ async function main() {
21
21
  console.error(`[MCPB] Parsing project: ${projectRoot}`);
22
22
  const parsedFiles = await parseProject(projectRoot);
23
23
  console.error(`[MCPB] Parsed ${parsedFiles.length} files`);
24
- const graph = buildGraph(parsedFiles);
24
+ const graph = buildGraph(parsedFiles, projectRoot);
25
25
  console.error(`[MCPB] Built graph: ${graph.order} symbols, ${graph.size} edges`);
26
26
  state.graph = graph;
27
27
  state.projectRoot = projectRoot;
package/dist/sdk.d.ts CHANGED
@@ -36,7 +36,7 @@ declare function parseProject(projectRoot: string, options?: {
36
36
  verbose?: boolean;
37
37
  }): Promise<ParsedFile[]>;
38
38
 
39
- declare function buildGraph(parsedFiles: ParsedFile[]): DirectedGraph;
39
+ declare function buildGraph(parsedFiles: ParsedFile[], projectRoot?: string): DirectedGraph;
40
40
 
41
41
  /**
42
42
  * Health Score Type Definitions
@@ -270,6 +270,35 @@ interface SecurityScanOptions {
270
270
 
271
271
  declare function scanSecurity(projectRoot: string, graph: DirectedGraph, options?: SecurityScanOptions): Promise<SecurityScanResult>;
272
272
 
273
+ type CrossLanguageEdgeType = 'rest-api' | 'subprocess';
274
+ interface CrossLanguageEdge {
275
+ sourceFile: string;
276
+ targetFile: string;
277
+ edgeType: CrossLanguageEdgeType;
278
+ confidence: 'high' | 'medium' | 'low';
279
+ sourceLanguage: string;
280
+ targetLanguage: string;
281
+ sourceLine?: number;
282
+ targetLine?: number;
283
+ metadata: {
284
+ httpMethod?: string;
285
+ path?: string;
286
+ command?: string;
287
+ calledFile?: string;
288
+ };
289
+ }
290
+ interface CrossLanguageDetectionResult {
291
+ edges: CrossLanguageEdge[];
292
+ stats: {
293
+ restApiEdges: number;
294
+ subprocessEdges: number;
295
+ filesAnalyzed: number;
296
+ detectionTimeMs: number;
297
+ };
298
+ }
299
+
300
+ declare function detectCrossLanguageEdges(files: ParsedFile[], projectRoot: string, graph: DirectedGraph): CrossLanguageDetectionResult;
301
+
273
302
  /**
274
303
  * depwire-cli SDK — Public API Surface
275
304
  *
@@ -282,4 +311,4 @@ declare function scanSecurity(projectRoot: string, graph: DirectedGraph, options
282
311
  /** Current SDK version — matches depwire-cli npm version */
283
312
  declare const DepwireSDKVersion: string;
284
313
 
285
- export { type BrokenImport, DepwireSDKVersion, type GraphDiff, type HealthDelta, type SecurityFinding, type SecurityScanOptions, type SecurityScanResult, type Severity, type SimulationAction, SimulationEngine, type SimulationResult, type VulnerabilityClass, analyzeDeadCode, buildGraph, calculateHealthScore, generateDocs, getArchitectureSummary, getImpact, parseProject, scanSecurity, searchSymbols };
314
+ export { type BrokenImport, type CrossLanguageDetectionResult, type CrossLanguageEdge, DepwireSDKVersion, type GraphDiff, type HealthDelta, type SecurityFinding, type SecurityScanOptions, type SecurityScanResult, type Severity, type SimulationAction, SimulationEngine, type SimulationResult, type VulnerabilityClass, analyzeDeadCode, buildGraph, calculateHealthScore, detectCrossLanguageEdges, generateDocs, getArchitectureSummary, getImpact, parseProject, scanSecurity, searchSymbols };
package/dist/sdk.js CHANGED
@@ -3,13 +3,14 @@ import {
3
3
  analyzeDeadCode,
4
4
  buildGraph,
5
5
  calculateHealthScore,
6
+ detectCrossLanguageEdges,
6
7
  generateDocs,
7
8
  getArchitectureSummary,
8
9
  getImpact,
9
10
  parseProject,
10
11
  scanSecurity,
11
12
  searchSymbols
12
- } from "./chunk-DA5LWNJ4.js";
13
+ } from "./chunk-ITEGMPF7.js";
13
14
 
14
15
  // src/sdk.ts
15
16
  import { readFileSync } from "fs";
@@ -25,6 +26,7 @@ export {
25
26
  analyzeDeadCode,
26
27
  buildGraph,
27
28
  calculateHealthScore,
29
+ detectCrossLanguageEdges,
28
30
  generateDocs,
29
31
  getArchitectureSummary,
30
32
  getImpact,
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "depwire-cli",
3
- "version": "0.9.27",
3
+ "version": "0.9.28",
4
4
  "description": "Dependency graph + 17 MCP tools for AI coding assistants. Impact analysis, health scoring, security scanner.",
5
5
  "type": "module",
6
6
  "bin": {