@mycodemap/mycodemap 0.4.1 → 0.5.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (309) hide show
  1. package/CHANGELOG.md +100 -0
  2. package/README.md +307 -243
  3. package/dist/ai/claude.d.ts +38 -0
  4. package/dist/ai/claude.d.ts.map +1 -0
  5. package/dist/ai/claude.js +169 -0
  6. package/dist/ai/claude.js.map +1 -0
  7. package/dist/ai/codex.d.ts +38 -0
  8. package/dist/ai/codex.d.ts.map +1 -0
  9. package/dist/ai/codex.js +169 -0
  10. package/dist/ai/codex.js.map +1 -0
  11. package/dist/ai/factory.d.ts +48 -0
  12. package/dist/ai/factory.d.ts.map +1 -0
  13. package/dist/ai/factory.js +95 -0
  14. package/dist/ai/factory.js.map +1 -0
  15. package/dist/ai/index.d.ts +12 -0
  16. package/dist/ai/index.d.ts.map +1 -0
  17. package/dist/ai/index.js +29 -0
  18. package/dist/ai/index.js.map +1 -0
  19. package/dist/ai/provider.d.ts +70 -0
  20. package/dist/ai/provider.d.ts.map +1 -0
  21. package/dist/ai/provider.js +31 -0
  22. package/dist/ai/provider.js.map +1 -0
  23. package/dist/ai/subagent-caller.d.ts +90 -0
  24. package/dist/ai/subagent-caller.d.ts.map +1 -0
  25. package/dist/ai/subagent-caller.js +280 -0
  26. package/dist/ai/subagent-caller.js.map +1 -0
  27. package/dist/ai/types.d.ts +70 -0
  28. package/dist/ai/types.d.ts.map +1 -0
  29. package/dist/ai/types.js +5 -0
  30. package/dist/ai/types.js.map +1 -0
  31. package/dist/cli/commands/analyze-options.d.ts +36 -0
  32. package/dist/cli/commands/analyze-options.d.ts.map +1 -0
  33. package/dist/cli/commands/analyze-options.js +147 -0
  34. package/dist/cli/commands/analyze-options.js.map +1 -0
  35. package/dist/cli/commands/analyze.d.ts +93 -4
  36. package/dist/cli/commands/analyze.d.ts.map +1 -1
  37. package/dist/cli/commands/analyze.js +592 -176
  38. package/dist/cli/commands/analyze.js.map +1 -1
  39. package/dist/cli/commands/ci.d.ts +47 -1
  40. package/dist/cli/commands/ci.d.ts.map +1 -1
  41. package/dist/cli/commands/ci.js +208 -1
  42. package/dist/cli/commands/ci.js.map +1 -1
  43. package/dist/cli/commands/design.d.ts +47 -0
  44. package/dist/cli/commands/design.d.ts.map +1 -0
  45. package/dist/cli/commands/design.js +268 -0
  46. package/dist/cli/commands/design.js.map +1 -0
  47. package/dist/cli/commands/export.d.ts.map +1 -1
  48. package/dist/cli/commands/export.js +2 -2
  49. package/dist/cli/commands/export.js.map +1 -1
  50. package/dist/cli/commands/generate.d.ts +8 -2
  51. package/dist/cli/commands/generate.d.ts.map +1 -1
  52. package/dist/cli/commands/generate.js +151 -22
  53. package/dist/cli/commands/generate.js.map +1 -1
  54. package/dist/cli/commands/init.d.ts.map +1 -1
  55. package/dist/cli/commands/init.js +2 -13
  56. package/dist/cli/commands/init.js.map +1 -1
  57. package/dist/cli/commands/server.d.ts.map +1 -1
  58. package/dist/cli/commands/server.js +2 -5
  59. package/dist/cli/commands/server.js.map +1 -1
  60. package/dist/cli/commands/ship/checker.d.ts.map +1 -1
  61. package/dist/cli/commands/ship/checker.js +0 -3
  62. package/dist/cli/commands/ship/checker.js.map +1 -1
  63. package/dist/cli/commands/ship/pipeline.d.ts.map +1 -1
  64. package/dist/cli/commands/ship/pipeline.js +8 -1
  65. package/dist/cli/commands/ship/pipeline.js.map +1 -1
  66. package/dist/cli/commands/ship/publisher.d.ts +9 -1
  67. package/dist/cli/commands/ship/publisher.d.ts.map +1 -1
  68. package/dist/cli/commands/ship/publisher.js +149 -6
  69. package/dist/cli/commands/ship/publisher.js.map +1 -1
  70. package/dist/cli/commands/ship/rules/quality-rules.d.ts +0 -1
  71. package/dist/cli/commands/ship/rules/quality-rules.d.ts.map +1 -1
  72. package/dist/cli/commands/ship/rules/quality-rules.js +4 -76
  73. package/dist/cli/commands/ship/rules/quality-rules.js.map +1 -1
  74. package/dist/cli/commands/workflow.js +4 -4
  75. package/dist/cli/commands/workflow.js.map +1 -1
  76. package/dist/cli/config-loader.d.ts +31 -0
  77. package/dist/cli/config-loader.d.ts.map +1 -0
  78. package/dist/cli/config-loader.js +235 -0
  79. package/dist/cli/config-loader.js.map +1 -0
  80. package/dist/cli/design-contract-loader.d.ts +15 -0
  81. package/dist/cli/design-contract-loader.d.ts.map +1 -0
  82. package/dist/cli/design-contract-loader.js +175 -0
  83. package/dist/cli/design-contract-loader.js.map +1 -0
  84. package/dist/cli/design-contract-schema.d.ts +11 -0
  85. package/dist/cli/design-contract-schema.d.ts.map +1 -0
  86. package/dist/cli/design-contract-schema.js +75 -0
  87. package/dist/cli/design-contract-schema.js.map +1 -0
  88. package/dist/cli/design-handoff-builder.d.ts +15 -0
  89. package/dist/cli/design-handoff-builder.d.ts.map +1 -0
  90. package/dist/cli/design-handoff-builder.js +345 -0
  91. package/dist/cli/design-handoff-builder.js.map +1 -0
  92. package/dist/cli/design-scope-resolver.d.ts +8 -0
  93. package/dist/cli/design-scope-resolver.d.ts.map +1 -0
  94. package/dist/cli/design-scope-resolver.js +712 -0
  95. package/dist/cli/design-scope-resolver.js.map +1 -0
  96. package/dist/cli/design-verification-builder.d.ts +8 -0
  97. package/dist/cli/design-verification-builder.d.ts.map +1 -0
  98. package/dist/cli/design-verification-builder.js +369 -0
  99. package/dist/cli/design-verification-builder.js.map +1 -0
  100. package/dist/cli/index.js +20 -63
  101. package/dist/cli/index.js.map +1 -1
  102. package/dist/cli/removed-commands.d.ts +9 -0
  103. package/dist/cli/removed-commands.d.ts.map +1 -0
  104. package/dist/cli/removed-commands.js +48 -0
  105. package/dist/cli/removed-commands.js.map +1 -0
  106. package/dist/cli/storage-runtime.d.ts +8 -0
  107. package/dist/cli/storage-runtime.d.ts.map +1 -0
  108. package/dist/cli/storage-runtime.js +14 -0
  109. package/dist/cli/storage-runtime.js.map +1 -0
  110. package/dist/cli/tree-sitter-check.d.ts.map +1 -1
  111. package/dist/cli/tree-sitter-check.js +0 -1
  112. package/dist/cli/tree-sitter-check.js.map +1 -1
  113. package/dist/cli-new/commands/export.d.ts.map +1 -1
  114. package/dist/cli-new/commands/export.js +2 -2
  115. package/dist/cli-new/commands/export.js.map +1 -1
  116. package/dist/cli-new/commands/query.d.ts.map +1 -1
  117. package/dist/cli-new/commands/query.js +5 -4
  118. package/dist/cli-new/commands/query.js.map +1 -1
  119. package/dist/cli-new/commands/server.d.ts.map +1 -1
  120. package/dist/cli-new/commands/server.js +2 -6
  121. package/dist/cli-new/commands/server.js.map +1 -1
  122. package/dist/cli-new/index.d.ts.map +1 -1
  123. package/dist/cli-new/index.js +0 -2
  124. package/dist/cli-new/index.js.map +1 -1
  125. package/dist/core/analyzer.d.ts.map +1 -1
  126. package/dist/core/analyzer.js +7 -39
  127. package/dist/core/analyzer.js.map +1 -1
  128. package/dist/core/file-discovery.d.ts +17 -0
  129. package/dist/core/file-discovery.d.ts.map +1 -0
  130. package/dist/core/file-discovery.js +75 -0
  131. package/dist/core/file-discovery.js.map +1 -0
  132. package/dist/core/global-index.d.ts +5 -0
  133. package/dist/core/global-index.d.ts.map +1 -1
  134. package/dist/core/global-index.js +71 -21
  135. package/dist/core/global-index.js.map +1 -1
  136. package/dist/generator/ai-overview.d.ts +51 -0
  137. package/dist/generator/ai-overview.d.ts.map +1 -0
  138. package/dist/generator/ai-overview.js +160 -0
  139. package/dist/generator/ai-overview.js.map +1 -0
  140. package/dist/generator/index.d.ts.map +1 -1
  141. package/dist/generator/index.js +8 -0
  142. package/dist/generator/index.js.map +1 -1
  143. package/dist/infrastructure/parser/implementations/GoParser.d.ts +2 -5
  144. package/dist/infrastructure/parser/implementations/GoParser.d.ts.map +1 -1
  145. package/dist/infrastructure/parser/implementations/GoParser.js +2 -5
  146. package/dist/infrastructure/parser/implementations/GoParser.js.map +1 -1
  147. package/dist/infrastructure/parser/implementations/PythonParser.d.ts +1 -5
  148. package/dist/infrastructure/parser/implementations/PythonParser.d.ts.map +1 -1
  149. package/dist/infrastructure/parser/implementations/PythonParser.js +1 -5
  150. package/dist/infrastructure/parser/implementations/PythonParser.js.map +1 -1
  151. package/dist/infrastructure/parser/implementations/TypeScriptParser.d.ts +1 -5
  152. package/dist/infrastructure/parser/implementations/TypeScriptParser.d.ts.map +1 -1
  153. package/dist/infrastructure/parser/implementations/TypeScriptParser.js +1 -5
  154. package/dist/infrastructure/parser/implementations/TypeScriptParser.js.map +1 -1
  155. package/dist/infrastructure/storage/StorageFactory.d.ts +12 -6
  156. package/dist/infrastructure/storage/StorageFactory.d.ts.map +1 -1
  157. package/dist/infrastructure/storage/StorageFactory.js +59 -43
  158. package/dist/infrastructure/storage/StorageFactory.js.map +1 -1
  159. package/dist/infrastructure/storage/adapters/FileSystemStorage.d.ts.map +1 -1
  160. package/dist/infrastructure/storage/adapters/FileSystemStorage.js +24 -137
  161. package/dist/infrastructure/storage/adapters/FileSystemStorage.js.map +1 -1
  162. package/dist/infrastructure/storage/adapters/KuzuDBStorage.d.ts +10 -18
  163. package/dist/infrastructure/storage/adapters/KuzuDBStorage.d.ts.map +1 -1
  164. package/dist/infrastructure/storage/adapters/KuzuDBStorage.js +103 -146
  165. package/dist/infrastructure/storage/adapters/KuzuDBStorage.js.map +1 -1
  166. package/dist/infrastructure/storage/adapters/MemoryStorage.d.ts +0 -1
  167. package/dist/infrastructure/storage/adapters/MemoryStorage.d.ts.map +1 -1
  168. package/dist/infrastructure/storage/adapters/MemoryStorage.js +16 -136
  169. package/dist/infrastructure/storage/adapters/MemoryStorage.js.map +1 -1
  170. package/dist/infrastructure/storage/adapters/Neo4jStorage.d.ts +9 -17
  171. package/dist/infrastructure/storage/adapters/Neo4jStorage.d.ts.map +1 -1
  172. package/dist/infrastructure/storage/adapters/Neo4jStorage.js +78 -138
  173. package/dist/infrastructure/storage/adapters/Neo4jStorage.js.map +1 -1
  174. package/dist/infrastructure/storage/graph-helpers.d.ts +16 -0
  175. package/dist/infrastructure/storage/graph-helpers.d.ts.map +1 -0
  176. package/dist/infrastructure/storage/graph-helpers.js +161 -0
  177. package/dist/infrastructure/storage/graph-helpers.js.map +1 -0
  178. package/dist/infrastructure/storage/index.d.ts.map +1 -1
  179. package/dist/interface/config/index.d.ts +10 -1
  180. package/dist/interface/config/index.d.ts.map +1 -1
  181. package/dist/interface/types/design-contract.d.ts +68 -0
  182. package/dist/interface/types/design-contract.d.ts.map +1 -0
  183. package/dist/interface/types/design-contract.js +7 -0
  184. package/dist/interface/types/design-contract.js.map +1 -0
  185. package/dist/interface/types/design-handoff.d.ts +68 -0
  186. package/dist/interface/types/design-handoff.d.ts.map +1 -0
  187. package/dist/interface/types/design-handoff.js +4 -0
  188. package/dist/interface/types/design-handoff.js.map +1 -0
  189. package/dist/interface/types/design-mapping.d.ts +51 -0
  190. package/dist/interface/types/design-mapping.d.ts.map +1 -0
  191. package/dist/interface/types/design-mapping.js +4 -0
  192. package/dist/interface/types/design-mapping.js.map +1 -0
  193. package/dist/interface/types/design-verification.d.ts +49 -0
  194. package/dist/interface/types/design-verification.d.ts.map +1 -0
  195. package/dist/interface/types/design-verification.js +4 -0
  196. package/dist/interface/types/design-verification.js.map +1 -0
  197. package/dist/interface/types/index.d.ts +17 -0
  198. package/dist/interface/types/index.d.ts.map +1 -1
  199. package/dist/interface/types/storage.d.ts +1 -4
  200. package/dist/interface/types/storage.d.ts.map +1 -1
  201. package/dist/orchestrator/ai-feed-generator.d.ts +210 -0
  202. package/dist/orchestrator/ai-feed-generator.d.ts.map +1 -0
  203. package/dist/orchestrator/ai-feed-generator.js +377 -0
  204. package/dist/orchestrator/ai-feed-generator.js.map +1 -0
  205. package/dist/orchestrator/confidence.d.ts +9 -9
  206. package/dist/orchestrator/confidence.d.ts.map +1 -1
  207. package/dist/orchestrator/confidence.js +44 -67
  208. package/dist/orchestrator/confidence.js.map +1 -1
  209. package/dist/orchestrator/file-header-scanner.d.ts.map +1 -1
  210. package/dist/orchestrator/file-header-scanner.js +22 -31
  211. package/dist/orchestrator/file-header-scanner.js.map +1 -1
  212. package/dist/orchestrator/intent-router.d.ts +2 -11
  213. package/dist/orchestrator/intent-router.d.ts.map +1 -1
  214. package/dist/orchestrator/intent-router.js +58 -49
  215. package/dist/orchestrator/intent-router.js.map +1 -1
  216. package/dist/orchestrator/tool-orchestrator.d.ts.map +1 -1
  217. package/dist/orchestrator/tool-orchestrator.js +6 -4
  218. package/dist/orchestrator/tool-orchestrator.js.map +1 -1
  219. package/dist/orchestrator/types.d.ts +113 -2
  220. package/dist/orchestrator/types.d.ts.map +1 -1
  221. package/dist/orchestrator/types.js +29 -0
  222. package/dist/orchestrator/types.js.map +1 -1
  223. package/dist/orchestrator/workflow/config.d.ts +4 -12
  224. package/dist/orchestrator/workflow/config.d.ts.map +1 -1
  225. package/dist/orchestrator/workflow/config.js +4 -6
  226. package/dist/orchestrator/workflow/config.js.map +1 -1
  227. package/dist/orchestrator/workflow/git-analyzer.d.ts.map +1 -1
  228. package/dist/orchestrator/workflow/git-analyzer.js +9 -19
  229. package/dist/orchestrator/workflow/git-analyzer.js.map +1 -1
  230. package/dist/orchestrator/workflow/phase-inheritance.d.ts.map +1 -1
  231. package/dist/orchestrator/workflow/phase-inheritance.js +14 -23
  232. package/dist/orchestrator/workflow/phase-inheritance.js.map +1 -1
  233. package/dist/orchestrator/workflow/result-fusion.d.ts.map +1 -1
  234. package/dist/orchestrator/workflow/result-fusion.js +9 -11
  235. package/dist/orchestrator/workflow/result-fusion.js.map +1 -1
  236. package/dist/orchestrator/workflow/templates.d.ts +4 -1
  237. package/dist/orchestrator/workflow/templates.d.ts.map +1 -1
  238. package/dist/orchestrator/workflow/templates.js +49 -207
  239. package/dist/orchestrator/workflow/templates.js.map +1 -1
  240. package/dist/orchestrator/workflow/test-linker.d.ts.map +1 -1
  241. package/dist/orchestrator/workflow/test-linker.js +12 -24
  242. package/dist/orchestrator/workflow/test-linker.js.map +1 -1
  243. package/dist/orchestrator/workflow/types.d.ts +11 -8
  244. package/dist/orchestrator/workflow/types.d.ts.map +1 -1
  245. package/dist/orchestrator/workflow/types.js +8 -1
  246. package/dist/orchestrator/workflow/types.js.map +1 -1
  247. package/dist/orchestrator/workflow/visualizer.d.ts.map +1 -1
  248. package/dist/orchestrator/workflow/visualizer.js +7 -9
  249. package/dist/orchestrator/workflow/visualizer.js.map +1 -1
  250. package/dist/orchestrator/workflow/workflow-context.d.ts.map +1 -1
  251. package/dist/orchestrator/workflow/workflow-context.js +3 -5
  252. package/dist/orchestrator/workflow/workflow-context.js.map +1 -1
  253. package/dist/orchestrator/workflow/workflow-orchestrator.d.ts +0 -4
  254. package/dist/orchestrator/workflow/workflow-orchestrator.d.ts.map +1 -1
  255. package/dist/orchestrator/workflow/workflow-orchestrator.js +7 -99
  256. package/dist/orchestrator/workflow/workflow-orchestrator.js.map +1 -1
  257. package/dist/parser/index.d.ts.map +1 -1
  258. package/dist/parser/index.js +2 -2
  259. package/dist/parser/index.js.map +1 -1
  260. package/dist/plugins/index.d.ts +5 -3
  261. package/dist/plugins/index.d.ts.map +1 -1
  262. package/dist/plugins/index.js +19 -8
  263. package/dist/plugins/index.js.map +1 -1
  264. package/dist/plugins/plugin-loader.d.ts +21 -6
  265. package/dist/plugins/plugin-loader.d.ts.map +1 -1
  266. package/dist/plugins/plugin-loader.js +170 -54
  267. package/dist/plugins/plugin-loader.js.map +1 -1
  268. package/dist/plugins/plugin-registry.d.ts +7 -4
  269. package/dist/plugins/plugin-registry.d.ts.map +1 -1
  270. package/dist/plugins/plugin-registry.js +62 -14
  271. package/dist/plugins/plugin-registry.js.map +1 -1
  272. package/dist/plugins/types.d.ts +16 -6
  273. package/dist/plugins/types.d.ts.map +1 -1
  274. package/dist/plugins/types.js +2 -0
  275. package/dist/plugins/types.js.map +1 -1
  276. package/dist/server/handlers/AnalysisHandler.d.ts +16 -2
  277. package/dist/server/handlers/AnalysisHandler.d.ts.map +1 -1
  278. package/dist/server/handlers/AnalysisHandler.js +31 -47
  279. package/dist/server/handlers/AnalysisHandler.js.map +1 -1
  280. package/dist/server/routes/api.d.ts.map +1 -1
  281. package/dist/server/routes/api.js +31 -12
  282. package/dist/server/routes/api.js.map +1 -1
  283. package/docs/AI_ASSISTANT_SETUP.md +3 -1
  284. package/docs/SETUP_GUIDE.md +41 -17
  285. package/docs/ai-guide/COMMANDS.md +179 -102
  286. package/docs/ai-guide/INTEGRATION.md +23 -21
  287. package/docs/ai-guide/OUTPUT.md +621 -10
  288. package/docs/ai-guide/PATTERNS.md +77 -18
  289. package/docs/ai-guide/PROMPTS.md +24 -18
  290. package/docs/ai-guide/QUICKSTART.md +35 -19
  291. package/docs/ai-guide/README.md +22 -4
  292. package/docs/archive/test-report-symbol-search.md +384 -0
  293. package/docs/archive/test-scenario-4-complexity-analysis.md +460 -0
  294. package/docs/archive/test_report_scenario5.md +615 -0
  295. package/docs/archive/test_scenario_3_impact_analysis_report.md +520 -0
  296. package/docs/product-specs/DESIGN_CONTRACT_TEMPLATE.md +79 -0
  297. package/docs/product-specs/MVP3-ARCHITECTURE-COMPARISON.md +159 -434
  298. package/docs/product-specs/MVP3-ARCHITECTURE-REDESIGN-PRD.md +169 -261
  299. package/docs/product-specs/MVP3-ARCHITECTURE-REDESIGN-TECH-PRD.md +201 -1259
  300. package/docs/product-specs/README.md +9 -1
  301. package/docs/rules/architecture-guardrails.md +1 -2
  302. package/docs/rules/engineering-with-codex-openai.md +20 -10
  303. package/docs/rules/validation.md +29 -4
  304. package/mycodemap.config.schema.json +76 -5
  305. package/package.json +1 -1
  306. package/scripts/experiments/arcadedb-http-smoke.mjs +90 -0
  307. package/scripts/sync-analyze-docs.js +500 -0
  308. package/scripts/validate-ai-docs.js +54 -1
  309. package/scripts/validate-docs.js +992 -25
@@ -2,18 +2,22 @@
2
2
  * [META] AnalyzeCommand - 统一分析入口
3
3
  * [WHY] 为 CI 与人工调用提供统一分析输出,支持 machine/json 契约
4
4
  */
5
+ import { readFile } from 'node:fs/promises';
6
+ import path from 'node:path';
5
7
  import { parseArgs } from 'node:util';
6
8
  import chalk from 'chalk';
7
9
  import { ImpactCommand } from './impact.js';
8
10
  import { DepsCommand } from './deps.js';
9
11
  import { ComplexityCommand } from './complexity.js';
12
+ import { ANALYZE_PARSE_OPTIONS, getAnalyzeHelpText } from './analyze-options.js';
13
+ import { PUBLIC_INTENTS, calculateConfidenceLevel } from '../../orchestrator/types.js';
10
14
  import { resolveTestFile } from '../../orchestrator/test-linker.js';
11
15
  import { ToolOrchestrator } from '../../orchestrator/tool-orchestrator.js';
12
16
  import { ResultFusion } from '../../orchestrator/result-fusion.js';
13
17
  import { CodemapAdapter } from '../../orchestrator/adapters/codemap-adapter.js';
14
18
  import { AstGrepAdapter } from '../../orchestrator/adapters/ast-grep-adapter.js';
15
19
  import { IntentRouter } from '../../orchestrator/intent-router.js';
16
- import { resolveOutputDir } from '../paths.js';
20
+ import { resolveDataPath, resolveOutputDir } from '../paths.js';
17
21
  /**
18
22
  * 错误码定义
19
23
  */
@@ -47,14 +51,7 @@ export const ERROR_MESSAGES = {
47
51
  * 支持的 intent 列表
48
52
  */
49
53
  export const VALID_INTENTS = [
50
- 'impact',
51
- 'dependency',
52
- 'search',
53
- 'documentation',
54
- 'complexity',
55
- 'overview',
56
- 'refactor',
57
- 'reference',
54
+ ...PUBLIC_INTENTS,
58
55
  ];
59
56
  /**
60
57
  * AnalyzeCommand 分析命令类
@@ -73,12 +70,30 @@ export class AnalyzeCommand {
73
70
  * @throws AnalyzeError 当参数无效时
74
71
  */
75
72
  validate() {
73
+ if (!this.args.intent) {
74
+ throw this.createError(AnalyzeErrorCode.E0002_MISSING_REQUIRED_PARAM, '缺少必要参数: intent');
75
+ }
76
+ const intentRouter = new IntentRouter();
76
77
  // 验证 intent
77
- if (this.args.intent && !VALID_INTENTS.includes(this.args.intent)) {
78
+ if (!intentRouter.isValidIntent(this.args.intent)) {
78
79
  throw this.createError(AnalyzeErrorCode.E0001_INVALID_INTENT, `无效的 intent: ${this.args.intent}。支持的选项: ${VALID_INTENTS.join(', ')}`);
79
80
  }
80
- // 验证 targets
81
- if (!this.args.targets || this.args.targets.length === 0) {
81
+ const routedIntent = intentRouter.route(this.args);
82
+ const normalizedIntent = routedIntent.intent;
83
+ const hasTargets = Boolean(this.args.targets && this.args.targets.length > 0);
84
+ const hasKeywords = Boolean(this.args.keywords && this.args.keywords.length > 0);
85
+ if (normalizedIntent === 'find') {
86
+ if (!hasTargets && !hasKeywords) {
87
+ throw this.createError(AnalyzeErrorCode.E0002_MISSING_REQUIRED_PARAM, '缺少必要参数: targets 或 keywords');
88
+ }
89
+ return;
90
+ }
91
+ if (normalizedIntent === 'link' &&
92
+ routedIntent.compatibility?.normalizedFrom === 'reference' &&
93
+ hasKeywords) {
94
+ return;
95
+ }
96
+ if (!hasTargets) {
82
97
  throw this.createError(AnalyzeErrorCode.E0002_MISSING_REQUIRED_PARAM, '缺少必要参数: targets');
83
98
  }
84
99
  }
@@ -95,33 +110,39 @@ export class AnalyzeCommand {
95
110
  */
96
111
  async execute() {
97
112
  this.validate();
98
- const intent = this.args.intent || 'impact';
99
- const scope = this.args.scope || 'direct';
113
+ const intentRouter = new IntentRouter();
114
+ const intentObj = intentRouter.route(this.args);
115
+ const scope = intentObj.scope;
100
116
  const topK = this.args.topK || 8;
101
- // 尝试使用 ToolOrchestrator 和 ResultFusion
102
- try {
103
- return await this.executeWithOrchestrator(intent, scope, topK);
104
- }
105
- catch (error) {
106
- // 回退到原有实现
107
- console.warn('[Analyze] Orchestrator not available, falling back to legacy mode');
108
- }
109
- // 根据 intent 路由 (legacy)
110
- switch (intent) {
111
- case 'impact':
112
- return this.executeImpact(scope, topK);
113
- case 'dependency':
114
- return this.executeDeps(topK);
115
- case 'complexity':
116
- return this.executeComplexity(topK);
117
+ switch (intentObj.intent) {
118
+ case 'read':
119
+ return this.executeRead(intentObj, scope, topK);
120
+ case 'link':
121
+ return this.executeLink(intentObj, topK);
122
+ case 'show':
123
+ return this.executeShow(intentObj, topK);
124
+ case 'find':
125
+ return this.executeFindWithFallback(intentObj, topK);
117
126
  default:
118
- return this.executeImpact(scope, topK);
127
+ throw this.createError(AnalyzeErrorCode.E0001_INVALID_INTENT, `无效的 intent: ${intentObj.intent}`);
128
+ }
129
+ }
130
+ /**
131
+ * `find` 优先走 orchestrator,失败时回退到 AstGrep 搜索
132
+ */
133
+ async executeFindWithFallback(intentObj, topK) {
134
+ try {
135
+ return this.withCompatibility(await this.executeWithOrchestrator(intentObj, topK), intentObj.compatibility);
136
+ }
137
+ catch {
138
+ console.warn('[Analyze] Orchestrator not available, falling back to AstGrep search');
139
+ return this.executeFind(intentObj, topK);
119
140
  }
120
141
  }
121
142
  /**
122
143
  * 使用编排器执行分析
123
144
  */
124
- async executeWithOrchestrator(intent, scope, topK) {
145
+ async executeWithOrchestrator(intentObj, topK) {
125
146
  const orchestrator = new ToolOrchestrator();
126
147
  // 注册适配器
127
148
  const codemapAdapter = new CodemapAdapter({ codemapPath: resolveOutputDir().outputDir });
@@ -129,13 +150,7 @@ export class AnalyzeCommand {
129
150
  orchestrator.registerAdapter(codemapAdapter);
130
151
  orchestrator.registerAdapter(astGrepAdapter);
131
152
  const fusion = new ResultFusion();
132
- const intentRouter = new IntentRouter();
133
- // 构建意图对象
134
- const intentObj = intentRouter.route({
135
- ...this.args,
136
- intent: intent,
137
- scope: scope,
138
- });
153
+ const effectiveIntent = intentObj.executionIntent ?? intentObj.intent;
139
154
  let orchestratedResults = [];
140
155
  let confidence;
141
156
  if (intentObj.secondary) {
@@ -143,7 +158,7 @@ export class AnalyzeCommand {
143
158
  const resultsByTool = await orchestrator.executeParallel(intentObj, tools);
144
159
  orchestratedResults = fusion.fuse(resultsByTool, {
145
160
  topK,
146
- intent: intentObj.intent,
161
+ intent: effectiveIntent,
147
162
  keywordWeights: {},
148
163
  maxTokens: 160,
149
164
  });
@@ -165,17 +180,525 @@ export class AnalyzeCommand {
165
180
  const resultsWithLocation = this.enrichWithLocation(orchestratedResults);
166
181
  return {
167
182
  schemaVersion: 'v1.0.0',
168
- intent: intent,
183
+ intent: intentObj.intent,
169
184
  tool: 'codemap-orchestrated',
170
185
  confidence,
171
186
  results: resultsWithLocation,
172
187
  metadata: {
173
188
  total: orchestratedResults.length,
174
- scope,
189
+ scope: intentObj.scope,
175
190
  resultCount: orchestratedResults.length,
176
191
  },
177
192
  };
178
193
  }
194
+ /**
195
+ * 为输出添加兼容期 warning
196
+ */
197
+ withCompatibility(output, compatibility) {
198
+ const warnings = this.buildCompatibilityWarnings(compatibility);
199
+ if (warnings.length === 0) {
200
+ return output;
201
+ }
202
+ return {
203
+ ...output,
204
+ warnings
205
+ };
206
+ }
207
+ /**
208
+ * 生成结构化兼容 warning
209
+ */
210
+ buildCompatibilityWarnings(compatibility) {
211
+ if (!compatibility?.isDeprecated || !compatibility.normalizedFrom) {
212
+ return [];
213
+ }
214
+ const replacementIntent = compatibility.normalizedFrom === 'search'
215
+ ? 'find'
216
+ : compatibility.normalizedFrom === 'impact' || compatibility.normalizedFrom === 'complexity'
217
+ ? 'read'
218
+ : compatibility.normalizedFrom === 'dependency' || compatibility.normalizedFrom === 'reference'
219
+ ? 'link'
220
+ : 'show';
221
+ return [{
222
+ code: 'deprecated-intent',
223
+ severity: 'warning',
224
+ message: `legacy intent "${compatibility.normalizedFrom}" 已弃用,请改用 "${replacementIntent}"`,
225
+ deprecatedIntent: compatibility.normalizedFrom,
226
+ replacementIntent,
227
+ sunsetPolicy: '2-minor-window'
228
+ }];
229
+ }
230
+ /**
231
+ * find fallback
232
+ */
233
+ async executeFind(intentObj, topK) {
234
+ const searchTerms = intentObj.keywords.length > 0 ? intentObj.keywords : intentObj.targets;
235
+ const adapter = new AstGrepAdapter({ includeTests: this.args.includeTests ?? true });
236
+ const rawResults = await adapter.execute(searchTerms, {
237
+ topK,
238
+ includeTests: this.args.includeTests,
239
+ keywords: searchTerms
240
+ });
241
+ const results = this.enrichWithLocation(rawResults).slice(0, topK);
242
+ const confidence = this.buildConfidence(this.calculateConfidence(results));
243
+ return this.withCompatibility({
244
+ schemaVersion: 'v1.0.0',
245
+ intent: 'find',
246
+ tool: 'ast-grep-find',
247
+ confidence,
248
+ results,
249
+ metadata: {
250
+ total: results.length,
251
+ resultCount: results.length,
252
+ scope: intentObj.scope
253
+ }
254
+ }, intentObj.compatibility);
255
+ }
256
+ /**
257
+ * 执行 read 聚合
258
+ */
259
+ async executeRead(intentObj, scope, topK) {
260
+ const [impactOutput, complexityOutput] = await Promise.all([
261
+ this.executeImpact(scope, topK),
262
+ this.executeComplexity(topK)
263
+ ]);
264
+ const mergedResults = this.mergeUnifiedResults(impactOutput.results, complexityOutput.results);
265
+ const results = mergedResults.slice(0, topK);
266
+ const analysis = {
267
+ intent: 'read',
268
+ impact: impactOutput.results
269
+ .filter(result => result.content.startsWith('被 '))
270
+ .map(result => ({
271
+ file: result.file,
272
+ location: result.location,
273
+ changedFiles: [result.file],
274
+ transitiveDependencies: result.metadata?.dependencies ?? [],
275
+ impactCount: result.metadata?.impactCount ?? 0,
276
+ risk: result.metadata?.riskLevel ?? 'low'
277
+ })),
278
+ complexity: complexityOutput.results
279
+ .filter(result => Boolean(result.metadata?.complexityMetrics))
280
+ .map(result => ({
281
+ file: result.file,
282
+ location: result.location,
283
+ metrics: result.metadata?.complexityMetrics ?? {
284
+ cyclomatic: 0,
285
+ cognitive: 0,
286
+ maintainability: 0
287
+ },
288
+ risk: result.metadata?.riskLevel ?? 'low'
289
+ }))
290
+ };
291
+ return this.withCompatibility({
292
+ schemaVersion: 'v1.0.0',
293
+ intent: 'read',
294
+ tool: 'codemap-read',
295
+ confidence: this.combineConfidence([impactOutput.confidence, complexityOutput.confidence], results),
296
+ results,
297
+ analysis,
298
+ metadata: {
299
+ total: mergedResults.length,
300
+ resultCount: results.length,
301
+ scope
302
+ }
303
+ }, intentObj.compatibility);
304
+ }
305
+ /**
306
+ * 执行 link 聚合
307
+ */
308
+ async executeLink(intentObj, topK) {
309
+ const dependencyOutput = intentObj.targets.length > 0
310
+ ? await this.executeDeps(Math.max(topK, intentObj.targets.length))
311
+ : this.createEmptyOutput('link', 'codemap-link', intentObj.scope);
312
+ const codeMap = await this.loadCodeMap();
313
+ const dependency = codeMap
314
+ ? this.buildLinkDependencyAnalysis(codeMap, intentObj.targets)
315
+ : [];
316
+ const reference = codeMap
317
+ ? this.buildLinkReferenceAnalysis(codeMap, intentObj.targets, intentObj.keywords)
318
+ : [];
319
+ const referenceResults = this.buildReferenceResults(reference);
320
+ const mergedResults = this.mergeUnifiedResults(dependencyOutput.results, referenceResults);
321
+ const results = mergedResults.slice(0, topK);
322
+ const confidence = this.combineConfidence([
323
+ dependencyOutput.confidence,
324
+ this.buildConfidence(this.calculateConfidence(referenceResults))
325
+ ], results);
326
+ const analysis = {
327
+ intent: 'link',
328
+ ...(reference.length > 0 ? { reference } : {}),
329
+ ...(dependency.length > 0 ? { dependency } : {})
330
+ };
331
+ return this.withCompatibility({
332
+ schemaVersion: 'v1.0.0',
333
+ intent: 'link',
334
+ tool: 'codemap-link',
335
+ confidence,
336
+ results,
337
+ analysis,
338
+ metadata: {
339
+ total: mergedResults.length,
340
+ resultCount: results.length,
341
+ scope: intentObj.scope
342
+ }
343
+ }, intentObj.compatibility);
344
+ }
345
+ /**
346
+ * 执行 show 聚合
347
+ */
348
+ async executeShow(intentObj, topK) {
349
+ const codeMap = await this.loadCodeMap();
350
+ const modules = codeMap ? this.findMatchingModules(codeMap, intentObj.targets) : [];
351
+ const analysis = {
352
+ intent: 'show',
353
+ overview: modules.map(module => ({
354
+ title: path.basename(module.absolutePath),
355
+ file: this.toRelativePath(codeMap, module.absolutePath),
356
+ overview: module.overview ?? `模块 ${this.toRelativePath(codeMap, module.absolutePath)},导出 ${module.exports.length} 个符号,依赖 ${module.dependencies.length} 个模块`,
357
+ exports: module.exports.map(exp => exp.name)
358
+ })),
359
+ documentation: modules.map(module => ({
360
+ title: path.basename(module.absolutePath),
361
+ file: this.toRelativePath(codeMap, module.absolutePath),
362
+ content: module.overview
363
+ ?? `类型: ${module.type}; 代码行: ${module.stats.codeLines}; 导出: ${module.exports.map(exp => exp.name).join(', ') || '无'}`
364
+ }))
365
+ };
366
+ const results = this.buildShowResults(analysis).slice(0, topK);
367
+ return this.withCompatibility({
368
+ schemaVersion: 'v1.0.0',
369
+ intent: 'show',
370
+ tool: 'codemap-show',
371
+ confidence: this.buildConfidence(this.calculateConfidence(results)),
372
+ results,
373
+ analysis,
374
+ metadata: {
375
+ total: results.length,
376
+ resultCount: results.length,
377
+ scope: intentObj.scope
378
+ }
379
+ }, intentObj.compatibility);
380
+ }
381
+ /**
382
+ * 创建空输出
383
+ */
384
+ createEmptyOutput(intent, tool, scope) {
385
+ return {
386
+ schemaVersion: 'v1.0.0',
387
+ intent,
388
+ tool,
389
+ confidence: this.buildConfidence(0),
390
+ results: [],
391
+ metadata: {
392
+ total: 0,
393
+ resultCount: 0,
394
+ scope
395
+ }
396
+ };
397
+ }
398
+ /**
399
+ * 聚合多个 Confidence
400
+ */
401
+ combineConfidence(confidences, results) {
402
+ const effective = confidences.filter(confidence => Number.isFinite(confidence.score));
403
+ if (effective.length === 0) {
404
+ return this.buildConfidence(this.calculateConfidence(results));
405
+ }
406
+ const score = Math.round((effective.reduce((sum, confidence) => sum + confidence.score, 0) / effective.length) * 100) / 100;
407
+ return this.buildConfidence(score);
408
+ }
409
+ /**
410
+ * 构建 Confidence
411
+ */
412
+ buildConfidence(score) {
413
+ const normalizedScore = Math.round(Math.max(0, Math.min(score, 1)) * 100) / 100;
414
+ return {
415
+ score: normalizedScore,
416
+ level: calculateConfidenceLevel(normalizedScore)
417
+ };
418
+ }
419
+ /**
420
+ * 合并 UnifiedResult
421
+ */
422
+ mergeUnifiedResults(...collections) {
423
+ const merged = new Map();
424
+ for (const results of collections) {
425
+ for (const result of results) {
426
+ const key = `${result.file}:${result.location?.line ?? result.line ?? 1}`;
427
+ const existing = merged.get(key);
428
+ if (!existing || result.relevance > existing.relevance) {
429
+ merged.set(key, result);
430
+ }
431
+ }
432
+ }
433
+ return Array.from(merged.values()).sort((left, right) => right.relevance - left.relevance);
434
+ }
435
+ /**
436
+ * 加载 CodeMap 数据
437
+ */
438
+ async loadCodeMap() {
439
+ try {
440
+ const dataPath = resolveDataPath();
441
+ const raw = await readFile(dataPath, 'utf-8');
442
+ return JSON.parse(raw);
443
+ }
444
+ catch {
445
+ return null;
446
+ }
447
+ }
448
+ /**
449
+ * 查找目标模块
450
+ */
451
+ findMatchingModules(codeMap, targets) {
452
+ const seen = new Set();
453
+ const modules = [];
454
+ for (const target of targets) {
455
+ const module = this.findMatchingModule(codeMap, target);
456
+ if (module && !seen.has(module.id)) {
457
+ seen.add(module.id);
458
+ modules.push(module);
459
+ }
460
+ }
461
+ return modules;
462
+ }
463
+ /**
464
+ * 查找单个匹配模块
465
+ */
466
+ findMatchingModule(codeMap, target) {
467
+ return codeMap.modules.find(module => {
468
+ const relativePath = this.toRelativePath(codeMap, module.absolutePath);
469
+ return module.absolutePath.includes(target) || relativePath.includes(target);
470
+ });
471
+ }
472
+ /**
473
+ * 构建 link dependency analysis
474
+ */
475
+ buildLinkDependencyAnalysis(codeMap, targets) {
476
+ return this.findMatchingModules(codeMap, targets).map(module => ({
477
+ file: this.toRelativePath(codeMap, module.absolutePath),
478
+ location: {
479
+ file: this.toRelativePath(codeMap, module.absolutePath),
480
+ line: 1,
481
+ column: 1
482
+ },
483
+ imports: module.dependencies,
484
+ importedBy: module.dependents.map(id => {
485
+ const dependent = codeMap.modules.find(candidate => candidate.id === id);
486
+ return dependent ? this.toRelativePath(codeMap, dependent.absolutePath) : id;
487
+ }),
488
+ cycles: []
489
+ }));
490
+ }
491
+ /**
492
+ * 构建 link reference analysis
493
+ */
494
+ buildLinkReferenceAnalysis(codeMap, targets, keywords) {
495
+ const items = [];
496
+ for (const module of this.findMatchingModules(codeMap, targets)) {
497
+ items.push(this.buildModuleReferenceItem(codeMap, module));
498
+ }
499
+ for (const keyword of keywords) {
500
+ items.push(this.buildKeywordReferenceItem(codeMap, keyword));
501
+ }
502
+ const merged = new Map();
503
+ for (const item of items) {
504
+ const existing = merged.get(item.target);
505
+ if (!existing) {
506
+ merged.set(item.target, item);
507
+ continue;
508
+ }
509
+ merged.set(item.target, {
510
+ target: item.target,
511
+ callers: Array.from(new Set([...existing.callers, ...item.callers])),
512
+ callees: Array.from(new Set([...existing.callees, ...item.callees])),
513
+ matches: [...existing.matches, ...item.matches]
514
+ });
515
+ }
516
+ return Array.from(merged.values());
517
+ }
518
+ /**
519
+ * 基于模块构建 reference item
520
+ */
521
+ buildModuleReferenceItem(codeMap, module) {
522
+ const relativePath = this.toRelativePath(codeMap, module.absolutePath);
523
+ const exportedSymbols = new Set(module.exports.map(exp => exp.name));
524
+ const matchTokens = new Set([
525
+ relativePath,
526
+ this.stripModuleExtension(relativePath),
527
+ path.basename(relativePath),
528
+ this.stripModuleExtension(path.basename(relativePath)),
529
+ module.id
530
+ ]);
531
+ const callers = new Set();
532
+ const matches = [];
533
+ for (const candidate of codeMap.modules) {
534
+ if (candidate.id === module.id) {
535
+ continue;
536
+ }
537
+ const candidatePath = this.toRelativePath(codeMap, candidate.absolutePath);
538
+ for (const entry of candidate.imports) {
539
+ const sourceMatched = this.matchesModuleSource(entry.source, matchTokens);
540
+ const symbolMatched = entry.specifiers.some(specifier => exportedSymbols.has(specifier.name));
541
+ if (!sourceMatched && !symbolMatched) {
542
+ continue;
543
+ }
544
+ callers.add(candidatePath);
545
+ matches.push({
546
+ file: candidatePath,
547
+ line: 1,
548
+ snippet: entry.source
549
+ });
550
+ }
551
+ }
552
+ return {
553
+ target: relativePath,
554
+ callers: Array.from(callers),
555
+ callees: module.dependencies,
556
+ matches
557
+ };
558
+ }
559
+ /**
560
+ * 基于关键词构建 reference item
561
+ */
562
+ buildKeywordReferenceItem(codeMap, keyword) {
563
+ const callers = new Set();
564
+ const callees = new Set();
565
+ const matches = [];
566
+ for (const module of codeMap.modules) {
567
+ const relativePath = this.toRelativePath(codeMap, module.absolutePath);
568
+ const definesKeyword = module.exports.some(exp => exp.name === keyword)
569
+ || module.symbols.some(symbol => symbol.name === keyword);
570
+ if (definesKeyword) {
571
+ callees.add(relativePath);
572
+ }
573
+ for (const entry of module.imports) {
574
+ const sourceMatched = entry.source.toLowerCase().includes(keyword.toLowerCase());
575
+ const specifierMatched = entry.specifiers.some(specifier => specifier.name === keyword || specifier.alias === keyword);
576
+ if (!sourceMatched && !specifierMatched) {
577
+ continue;
578
+ }
579
+ callers.add(relativePath);
580
+ matches.push({
581
+ file: relativePath,
582
+ line: 1,
583
+ snippet: entry.source
584
+ });
585
+ }
586
+ }
587
+ return {
588
+ target: keyword,
589
+ callers: Array.from(callers),
590
+ callees: Array.from(callees),
591
+ matches
592
+ };
593
+ }
594
+ /**
595
+ * 将 reference analysis 转为 results
596
+ */
597
+ buildReferenceResults(items) {
598
+ return items.map(item => ({
599
+ id: `reference-${item.target}`,
600
+ source: 'codemap',
601
+ toolScore: 0.8,
602
+ type: 'symbol',
603
+ file: item.matches[0]?.file ?? item.callees[0] ?? item.target,
604
+ line: item.matches[0]?.line ?? 1,
605
+ location: {
606
+ file: item.matches[0]?.file ?? item.callees[0] ?? item.target,
607
+ line: item.matches[0]?.line ?? 1,
608
+ column: 1
609
+ },
610
+ content: `发现 ${item.callers.length} 个引用方,${item.callees.length} 个关联目标`,
611
+ relevance: Math.min(0.4 + item.callers.length * 0.1, 0.95),
612
+ keywords: [item.target],
613
+ metadata: {
614
+ dependencies: item.callees,
615
+ impactCount: item.callers.length,
616
+ stability: true,
617
+ riskLevel: item.callers.length > 10 ? 'high' : item.callers.length > 3 ? 'medium' : 'low'
618
+ }
619
+ }));
620
+ }
621
+ /**
622
+ * 构建 show 结果
623
+ */
624
+ buildShowResults(analysis) {
625
+ const results = [];
626
+ for (const section of analysis.overview ?? []) {
627
+ results.push({
628
+ id: `show-overview-${section.file}`,
629
+ source: 'codemap',
630
+ toolScore: 0.75,
631
+ type: 'documentation',
632
+ file: section.file,
633
+ line: 1,
634
+ location: {
635
+ file: section.file,
636
+ line: 1,
637
+ column: 1
638
+ },
639
+ content: section.overview,
640
+ relevance: 0.75,
641
+ keywords: section.exports,
642
+ metadata: {
643
+ stability: true,
644
+ riskLevel: 'low'
645
+ }
646
+ });
647
+ }
648
+ for (const section of analysis.documentation ?? []) {
649
+ results.push({
650
+ id: `show-documentation-${section.file}`,
651
+ source: 'codemap',
652
+ toolScore: 0.7,
653
+ type: 'documentation',
654
+ file: section.file,
655
+ line: 1,
656
+ location: {
657
+ file: section.file,
658
+ line: 1,
659
+ column: 1
660
+ },
661
+ content: section.content,
662
+ relevance: 0.7,
663
+ keywords: [],
664
+ metadata: {
665
+ stability: true,
666
+ riskLevel: 'low'
667
+ }
668
+ });
669
+ }
670
+ return this.mergeUnifiedResults(results);
671
+ }
672
+ /**
673
+ * 转为相对路径
674
+ */
675
+ toRelativePath(codeMap, filePath) {
676
+ return path.relative(codeMap.project.rootDir, filePath).replace(/\\/g, '/');
677
+ }
678
+ /**
679
+ * 去除模块扩展名
680
+ */
681
+ stripModuleExtension(value) {
682
+ return value.replace(/\.[cm]?[jt]sx?$/i, '');
683
+ }
684
+ /**
685
+ * 判断 import source 是否引用目标模块
686
+ */
687
+ matchesModuleSource(source, tokens) {
688
+ const normalizedSource = this.stripModuleExtension(source).replace(/\\/g, '/').toLowerCase();
689
+ for (const token of tokens) {
690
+ const normalizedToken = this.stripModuleExtension(token).replace(/\\/g, '/').toLowerCase();
691
+ if (!normalizedToken) {
692
+ continue;
693
+ }
694
+ if (normalizedSource === normalizedToken
695
+ || normalizedSource.endsWith(normalizedToken)
696
+ || normalizedSource.includes(normalizedToken)) {
697
+ return true;
698
+ }
699
+ }
700
+ return false;
701
+ }
179
702
  /**
180
703
  * 为 UnifiedResult 添加 location 字段
181
704
  */
@@ -220,33 +743,16 @@ export class AnalyzeCommand {
220
743
  // 添加 location 字段
221
744
  const resultsWithLocation = this.enrichWithLocation(resultsWithTests);
222
745
  const typedResults = resultsWithLocation;
223
- // 输出格式处理
224
- if (this.args.outputMode === 'machine' || this.args.json) {
225
- return {
226
- schemaVersion: 'v1.0.0',
227
- intent: 'impact',
228
- tool: 'codemap-impact',
229
- confidence,
230
- results: typedResults.slice(0, topK),
231
- metadata: {
232
- total: resultsWithTests.length,
233
- scope,
234
- resultCount: resultsWithTests.length,
235
- },
236
- };
237
- }
238
- // 人类可读输出
239
- this.printHumanOutput(resultsWithTests, 'impact');
240
746
  return {
241
747
  schemaVersion: 'v1.0.0',
242
- intent: 'impact',
748
+ intent: 'read',
243
749
  tool: 'codemap-impact',
244
750
  confidence,
245
- results: typedResults,
751
+ results: typedResults.slice(0, topK),
246
752
  metadata: {
247
753
  total: resultsWithTests.length,
248
754
  scope,
249
- resultCount: resultsWithTests.length,
755
+ resultCount: typedResults.slice(0, topK).length,
250
756
  },
251
757
  };
252
758
  }
@@ -284,31 +790,15 @@ export class AnalyzeCommand {
284
790
  // 添加 location 字段
285
791
  const resultsWithLocation = this.enrichWithLocation(resultsWithTests);
286
792
  const typedResults = resultsWithLocation;
287
- // 输出格式处理
288
- if (this.args.outputMode === 'machine' || this.args.json) {
289
- return {
290
- schemaVersion: 'v1.0.0',
291
- intent: 'dependency',
292
- tool: 'codemap-deps',
293
- confidence,
294
- results: typedResults.slice(0, topK),
295
- metadata: {
296
- total: resultsWithTests.length,
297
- resultCount: resultsWithTests.length,
298
- },
299
- };
300
- }
301
- // 人类可读输出
302
- this.printHumanOutput(resultsWithTests, 'dependency');
303
793
  return {
304
794
  schemaVersion: 'v1.0.0',
305
- intent: 'dependency',
795
+ intent: 'link',
306
796
  tool: 'codemap-deps',
307
797
  confidence,
308
- results: typedResults,
798
+ results: typedResults.slice(0, topK),
309
799
  metadata: {
310
800
  total: resultsWithTests.length,
311
- resultCount: resultsWithTests.length,
801
+ resultCount: typedResults.slice(0, topK).length,
312
802
  },
313
803
  };
314
804
  }
@@ -332,31 +822,15 @@ export class AnalyzeCommand {
332
822
  // 添加 location 字段
333
823
  const resultsWithLocation = this.enrichWithLocation(resultsWithTests);
334
824
  const typedResults = resultsWithLocation;
335
- // 输出格式处理
336
- if (this.args.outputMode === 'machine' || this.args.json) {
337
- return {
338
- schemaVersion: 'v1.0.0',
339
- intent: 'complexity',
340
- tool: 'codemap-complexity',
341
- confidence,
342
- results: typedResults.slice(0, topK),
343
- metadata: {
344
- total: resultsWithTests.length,
345
- resultCount: resultsWithTests.length,
346
- },
347
- };
348
- }
349
- // 人类可读输出
350
- this.printHumanOutput(resultsWithTests, 'complexity');
351
825
  return {
352
826
  schemaVersion: 'v1.0.0',
353
- intent: 'complexity',
827
+ intent: 'read',
354
828
  tool: 'codemap-complexity',
355
829
  confidence,
356
- results: typedResults,
830
+ results: typedResults.slice(0, topK),
357
831
  metadata: {
358
832
  total: resultsWithTests.length,
359
- resultCount: resultsWithTests.length,
833
+ resultCount: typedResults.slice(0, topK).length,
360
834
  },
361
835
  };
362
836
  }
@@ -400,68 +874,31 @@ export class AnalyzeCommand {
400
874
  /**
401
875
  * 解析 CLI 参数
402
876
  */
877
+ function normalizeStringArray(value) {
878
+ if (typeof value === 'string') {
879
+ return [value];
880
+ }
881
+ if (Array.isArray(value)) {
882
+ return value.filter((item) => typeof item === 'string');
883
+ }
884
+ return [];
885
+ }
403
886
  export function parseAnalyzeArgs(argv) {
404
887
  try {
405
888
  const { values, positionals } = parseArgs({
406
- argv,
889
+ args: argv,
407
890
  allowPositionals: true,
408
- options: {
409
- intent: {
410
- type: 'string',
411
- short: 'i',
412
- },
413
- targets: {
414
- type: 'string',
415
- multiple: true,
416
- short: 't',
417
- },
418
- keywords: {
419
- type: 'string',
420
- multiple: true,
421
- short: 'k',
422
- },
423
- scope: {
424
- type: 'string',
425
- short: 's',
426
- },
427
- topK: {
428
- type: 'string',
429
- short: 'n',
430
- },
431
- 'include-tests': {
432
- type: 'boolean',
433
- default: false,
434
- },
435
- 'include-git-history': {
436
- type: 'boolean',
437
- default: false,
438
- },
439
- json: {
440
- type: 'boolean',
441
- default: false,
442
- },
443
- structured: {
444
- type: 'boolean',
445
- default: false,
446
- },
447
- 'output-mode': {
448
- type: 'string',
449
- },
450
- help: {
451
- type: 'boolean',
452
- short: 'h',
453
- default: false,
454
- },
455
- },
891
+ options: ANALYZE_PARSE_OPTIONS,
456
892
  });
457
893
  // 合并位置参数和 --targets 参数作为 targets
458
894
  const positionalTargets = positionals?.filter(p => !p.startsWith('-')) || [];
459
- const explicitTargets = values.targets ? (Array.isArray(values.targets) ? values.targets : [values.targets]) : [];
895
+ const explicitTargets = normalizeStringArray(values.targets);
460
896
  const allTargets = [...explicitTargets, ...positionalTargets];
897
+ const keywords = normalizeStringArray(values.keywords);
461
898
  return {
462
899
  intent: values.intent,
463
900
  targets: allTargets.length > 0 ? allTargets : undefined,
464
- keywords: values.keywords,
901
+ keywords: keywords.length > 0 ? keywords : undefined,
465
902
  scope: values.scope,
466
903
  topK: values.topK ? parseInt(values.topK, 10) : undefined,
467
904
  includeTests: values['include-tests'],
@@ -510,6 +947,9 @@ export async function analyzeCommand(argv) {
510
947
  else {
511
948
  // human 模式:打印格式化输出
512
949
  const typedOutput = output;
950
+ for (const warning of typedOutput.warnings || []) {
951
+ console.warn(chalk.yellow(`⚠️ ${warning.message}`));
952
+ }
513
953
  console.log(chalk.bold(`\n📊 ${typedOutput.intent?.toUpperCase() || 'ANALYSIS'} 分析结果\n`));
514
954
  for (const result of typedOutput.results || []) {
515
955
  const lineInfo = result.location?.line ? `:${result.location.line}` : '';
@@ -538,30 +978,6 @@ export async function analyzeCommand(argv) {
538
978
  * 打印帮助信息
539
979
  */
540
980
  function printHelp() {
541
- console.log(`
542
- ${chalk.bold('codemap analyze')} - 统一分析入口
543
-
544
- ${chalk.bold('用法:')}
545
- codemap analyze [选项]
546
-
547
- ${chalk.bold('选项:')}
548
- -i, --intent <type> 分析类型 (impact|dependency|search|documentation|complexity|overview|refactor|reference)
549
- -t, --targets <paths> 目标文件/模块路径 (多个)
550
- -k, --keywords <words> 搜索关键词 (多个)
551
- -s, --scope <scope> 范围 (direct|transitive)
552
- -n, --topK <number> 返回结果数量 (默认 8, 最大 100)
553
- --include-tests 包含测试文件
554
- --include-git-history 包含 Git 历史
555
- --json JSON 格式输出
556
- --structured 输出完全结构化的 JSON(移除自然语言字符串)
557
- --output-mode <mode> 输出模式 (machine|human)
558
- -h, --help 显示帮助
559
-
560
- ${chalk.bold('示例:')}
561
- codemap analyze -i impact -t src/index.ts
562
- codemap analyze -i dependency -t src/utils --scope transitive --json
563
- codemap analyze -i complexity -t src/ --include-tests
564
- codemap analyze -i search -k "SourceLocation" --json --structured
565
- `);
981
+ console.log(getAnalyzeHelpText());
566
982
  }
567
983
  //# sourceMappingURL=analyze.js.map