mcp-adr-analysis-server 2.0.3 → 2.0.6

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 (90) hide show
  1. package/dist/src/index.d.ts +28 -0
  2. package/dist/src/index.d.ts.map +1 -1
  3. package/dist/src/index.js +703 -325
  4. package/dist/src/index.js.map +1 -1
  5. package/dist/src/prompts/adr-suggestion-prompts.d.ts +1 -0
  6. package/dist/src/prompts/adr-suggestion-prompts.d.ts.map +1 -1
  7. package/dist/src/prompts/adr-suggestion-prompts.js +14 -6
  8. package/dist/src/prompts/adr-suggestion-prompts.js.map +1 -1
  9. package/dist/src/resources/index.d.ts.map +1 -1
  10. package/dist/src/resources/index.js +31 -15
  11. package/dist/src/resources/index.js.map +1 -1
  12. package/dist/src/tools/adr-suggestion-tool.d.ts +4 -1
  13. package/dist/src/tools/adr-suggestion-tool.d.ts.map +1 -1
  14. package/dist/src/tools/adr-suggestion-tool.js +72 -114
  15. package/dist/src/tools/adr-suggestion-tool.js.map +1 -1
  16. package/dist/src/tools/content-masking-tool.d.ts +7 -0
  17. package/dist/src/tools/content-masking-tool.d.ts.map +1 -1
  18. package/dist/src/tools/content-masking-tool.js +134 -17
  19. package/dist/src/tools/content-masking-tool.js.map +1 -1
  20. package/dist/src/tools/deployment-guidance-tool.d.ts +21 -0
  21. package/dist/src/tools/deployment-guidance-tool.d.ts.map +1 -0
  22. package/dist/src/tools/deployment-guidance-tool.js +289 -0
  23. package/dist/src/tools/deployment-guidance-tool.js.map +1 -0
  24. package/dist/src/tools/environment-analysis-tool.d.ts +4 -0
  25. package/dist/src/tools/environment-analysis-tool.d.ts.map +1 -1
  26. package/dist/src/tools/environment-analysis-tool.js +209 -25
  27. package/dist/src/tools/environment-analysis-tool.js.map +1 -1
  28. package/dist/src/tools/research-question-tool.d.ts +4 -0
  29. package/dist/src/tools/research-question-tool.d.ts.map +1 -1
  30. package/dist/src/tools/research-question-tool.js +42 -4
  31. package/dist/src/tools/research-question-tool.js.map +1 -1
  32. package/dist/src/tools/rule-generation-tool.d.ts +4 -0
  33. package/dist/src/tools/rule-generation-tool.d.ts.map +1 -1
  34. package/dist/src/tools/rule-generation-tool.js +136 -16
  35. package/dist/src/tools/rule-generation-tool.js.map +1 -1
  36. package/dist/src/tools/todo-management-tool.d.ts +166 -0
  37. package/dist/src/tools/todo-management-tool.d.ts.map +1 -0
  38. package/dist/src/tools/todo-management-tool.js +472 -0
  39. package/dist/src/tools/todo-management-tool.js.map +1 -0
  40. package/dist/src/types/conversation-context.d.ts +93 -0
  41. package/dist/src/types/conversation-context.d.ts.map +1 -0
  42. package/dist/src/types/conversation-context.js +101 -0
  43. package/dist/src/types/conversation-context.js.map +1 -0
  44. package/dist/src/utils/actual-file-operations.d.ts +40 -0
  45. package/dist/src/utils/actual-file-operations.d.ts.map +1 -0
  46. package/dist/src/utils/actual-file-operations.js +309 -0
  47. package/dist/src/utils/actual-file-operations.js.map +1 -0
  48. package/dist/src/utils/adr-discovery.d.ts +36 -0
  49. package/dist/src/utils/adr-discovery.d.ts.map +1 -0
  50. package/dist/src/utils/adr-discovery.js +237 -0
  51. package/dist/src/utils/adr-discovery.js.map +1 -0
  52. package/dist/src/utils/adr-suggestions.d.ts +2 -1
  53. package/dist/src/utils/adr-suggestions.d.ts.map +1 -1
  54. package/dist/src/utils/adr-suggestions.js +8 -2
  55. package/dist/src/utils/adr-suggestions.js.map +1 -1
  56. package/dist/src/utils/apply-cot-enhancement.d.ts +46 -0
  57. package/dist/src/utils/apply-cot-enhancement.d.ts.map +1 -0
  58. package/dist/src/utils/apply-cot-enhancement.js +165 -0
  59. package/dist/src/utils/apply-cot-enhancement.js.map +1 -0
  60. package/dist/src/utils/chain-of-thought-template.d.ts +48 -0
  61. package/dist/src/utils/chain-of-thought-template.d.ts.map +1 -0
  62. package/dist/src/utils/chain-of-thought-template.js +191 -0
  63. package/dist/src/utils/chain-of-thought-template.js.map +1 -0
  64. package/dist/src/utils/deployment-analysis.d.ts +1 -0
  65. package/dist/src/utils/deployment-analysis.d.ts.map +1 -1
  66. package/dist/src/utils/deployment-analysis.js +82 -39
  67. package/dist/src/utils/deployment-analysis.js.map +1 -1
  68. package/dist/src/utils/environment-analysis.d.ts +6 -1
  69. package/dist/src/utils/environment-analysis.d.ts.map +1 -1
  70. package/dist/src/utils/environment-analysis.js +176 -87
  71. package/dist/src/utils/environment-analysis.js.map +1 -1
  72. package/dist/src/utils/file-system.d.ts +1 -0
  73. package/dist/src/utils/file-system.d.ts.map +1 -1
  74. package/dist/src/utils/file-system.js +24 -47
  75. package/dist/src/utils/file-system.js.map +1 -1
  76. package/dist/src/utils/prompt-execution.d.ts.map +1 -1
  77. package/dist/src/utils/prompt-execution.js +67 -3
  78. package/dist/src/utils/prompt-execution.js.map +1 -1
  79. package/dist/src/utils/research-integration.d.ts +4 -0
  80. package/dist/src/utils/research-integration.d.ts.map +1 -1
  81. package/dist/src/utils/research-integration.js +275 -84
  82. package/dist/src/utils/research-integration.js.map +1 -1
  83. package/dist/src/utils/research-questions.d.ts.map +1 -1
  84. package/dist/src/utils/research-questions.js +134 -38
  85. package/dist/src/utils/research-questions.js.map +1 -1
  86. package/dist/src/utils/rule-generation.d.ts +2 -1
  87. package/dist/src/utils/rule-generation.d.ts.map +1 -1
  88. package/dist/src/utils/rule-generation.js +65 -36
  89. package/dist/src/utils/rule-generation.js.map +1 -1
  90. package/package.json +5 -5
package/dist/src/index.js CHANGED
@@ -10,7 +10,10 @@ import { Server } from '@modelcontextprotocol/sdk/server/index.js';
10
10
  import { StdioServerTransport } from '@modelcontextprotocol/sdk/server/stdio.js';
11
11
  import { CallToolRequestSchema, ListToolsRequestSchema, ListResourcesRequestSchema, ReadResourceRequestSchema, ListPromptsRequestSchema, GetPromptRequestSchema } from '@modelcontextprotocol/sdk/types.js';
12
12
  import { readFileSync } from 'fs';
13
+ import { fileURLToPath } from 'url';
14
+ import { dirname, join } from 'path';
13
15
  import { McpAdrError } from './types/index.js';
16
+ import { CONVERSATION_CONTEXT_SCHEMA } from './types/conversation-context.js';
14
17
  import { maskMcpResponse, createMaskingConfig } from './utils/output-masking.js';
15
18
  import { loadConfig, validateProjectPath, createLogger, printConfigSummary } from './utils/config.js';
16
19
  /**
@@ -18,10 +21,40 @@ import { loadConfig, validateProjectPath, createLogger, printConfigSummary } fro
18
21
  */
19
22
  function getPackageVersion() {
20
23
  try {
21
- const packageJson = JSON.parse(readFileSync('./package.json', 'utf-8'));
22
- return packageJson.version;
24
+ // Handle both Jest environment and normal execution
25
+ let currentDir;
26
+ if (typeof import.meta !== 'undefined' && import.meta.url) {
27
+ // Normal ESM execution
28
+ const __filename = fileURLToPath(import.meta.url);
29
+ currentDir = dirname(__filename);
30
+ }
31
+ else {
32
+ // Jest or other environments without import.meta support
33
+ // Use process.cwd() as fallback
34
+ currentDir = process.cwd();
35
+ }
36
+ // Try multiple possible locations for package.json
37
+ const possiblePaths = [
38
+ join(currentDir, 'package.json'),
39
+ join(currentDir, '..', 'package.json'),
40
+ join(currentDir, '..', '..', 'package.json'),
41
+ join(process.cwd(), 'package.json')
42
+ ];
43
+ for (const packageJsonPath of possiblePaths) {
44
+ try {
45
+ const packageJson = JSON.parse(readFileSync(packageJsonPath, 'utf-8'));
46
+ if (packageJson.name === 'mcp-adr-analysis-server') {
47
+ return packageJson.version;
48
+ }
49
+ }
50
+ catch {
51
+ // Try next path
52
+ }
53
+ }
54
+ return '2.0.2'; // fallback version
23
55
  }
24
- catch {
56
+ catch (error) {
57
+ console.error('Error reading package.json:', error);
25
58
  return '2.0.2'; // fallback version
26
59
  }
27
60
  }
@@ -142,7 +175,8 @@ export class McpAdrAnalysisServer {
142
175
  type: 'array',
143
176
  items: { type: 'string' },
144
177
  description: 'Specific analysis areas to focus on (e.g., ["security", "performance", "architecture", "dependencies"])'
145
- }
178
+ },
179
+ conversationContext: CONVERSATION_CONTEXT_SCHEMA
146
180
  },
147
181
  required: []
148
182
  }
@@ -517,7 +551,8 @@ export class McpAdrAnalysisServer {
517
551
  type: 'boolean',
518
552
  description: 'Enable Knowledge Generation for domain-specific insights',
519
553
  default: true
520
- }
554
+ },
555
+ conversationContext: CONVERSATION_CONTEXT_SCHEMA
521
556
  }
522
557
  }
523
558
  },
@@ -1151,6 +1186,207 @@ export class McpAdrAnalysisServer {
1151
1186
  },
1152
1187
  required: ['developmentPhase']
1153
1188
  }
1189
+ },
1190
+ {
1191
+ name: 'read_file',
1192
+ description: 'Read contents of a file',
1193
+ inputSchema: {
1194
+ type: 'object',
1195
+ properties: {
1196
+ path: {
1197
+ type: 'string',
1198
+ description: 'Path to the file to read'
1199
+ }
1200
+ },
1201
+ required: ['path']
1202
+ }
1203
+ },
1204
+ {
1205
+ name: 'write_file',
1206
+ description: 'Write content to a file',
1207
+ inputSchema: {
1208
+ type: 'object',
1209
+ properties: {
1210
+ path: {
1211
+ type: 'string',
1212
+ description: 'Path to the file to write'
1213
+ },
1214
+ content: {
1215
+ type: 'string',
1216
+ description: 'Content to write to the file'
1217
+ }
1218
+ },
1219
+ required: ['path', 'content']
1220
+ }
1221
+ },
1222
+ {
1223
+ name: 'list_directory',
1224
+ description: 'List contents of a directory',
1225
+ inputSchema: {
1226
+ type: 'object',
1227
+ properties: {
1228
+ path: {
1229
+ type: 'string',
1230
+ description: 'Path to the directory to list'
1231
+ }
1232
+ },
1233
+ required: ['path']
1234
+ }
1235
+ },
1236
+ {
1237
+ name: 'manage_todo',
1238
+ description: 'Manage TODO.md files with incremental updates, task status tracking, and smart merging',
1239
+ inputSchema: {
1240
+ type: 'object',
1241
+ properties: {
1242
+ operation: {
1243
+ type: 'string',
1244
+ enum: ['update_status', 'add_tasks', 'merge_adr_updates', 'sync_progress', 'analyze_progress'],
1245
+ description: 'Operation to perform on TODO.md'
1246
+ },
1247
+ todoPath: {
1248
+ type: 'string',
1249
+ default: 'todo.md',
1250
+ description: 'Path to TODO.md file'
1251
+ },
1252
+ updates: {
1253
+ type: 'array',
1254
+ items: {
1255
+ type: 'object',
1256
+ properties: {
1257
+ taskId: { type: 'string' },
1258
+ status: { type: 'string', enum: ['pending', 'in_progress', 'completed', 'blocked', 'cancelled'] },
1259
+ notes: { type: 'string' },
1260
+ assignee: { type: 'string' }
1261
+ },
1262
+ required: ['taskId', 'status']
1263
+ },
1264
+ description: 'Status updates to apply (for update_status operation)'
1265
+ },
1266
+ tasks: {
1267
+ type: 'array',
1268
+ items: {
1269
+ type: 'object',
1270
+ properties: {
1271
+ title: { type: 'string' },
1272
+ status: { type: 'string', enum: ['pending', 'in_progress', 'completed', 'blocked', 'cancelled'] },
1273
+ priority: { type: 'string', enum: ['low', 'medium', 'high', 'critical'] },
1274
+ category: { type: 'string' },
1275
+ assignee: { type: 'string' },
1276
+ notes: { type: 'string' },
1277
+ estimatedHours: { type: 'number' }
1278
+ },
1279
+ required: ['title', 'status']
1280
+ },
1281
+ description: 'New tasks to add (for add_tasks operation)'
1282
+ },
1283
+ section: {
1284
+ type: 'string',
1285
+ description: 'Section to add tasks to (for add_tasks operation)'
1286
+ },
1287
+ adrDirectory: {
1288
+ type: 'string',
1289
+ default: 'docs/adrs',
1290
+ description: 'ADR directory path (for merge_adr_updates and sync_progress operations)'
1291
+ },
1292
+ preserveCompleted: {
1293
+ type: 'boolean',
1294
+ default: true,
1295
+ description: 'Keep completed tasks during merge (for merge_adr_updates operation)'
1296
+ },
1297
+ preserveCustom: {
1298
+ type: 'boolean',
1299
+ default: true,
1300
+ description: 'Keep manually added tasks during merge (for merge_adr_updates operation)'
1301
+ },
1302
+ updateAdrs: {
1303
+ type: 'boolean',
1304
+ default: false,
1305
+ description: 'Update ADR status based on TODO progress (for sync_progress operation)'
1306
+ },
1307
+ timeframe: {
1308
+ type: 'string',
1309
+ enum: ['day', 'week', 'month', 'all'],
1310
+ default: 'week',
1311
+ description: 'Analysis timeframe (for analyze_progress operation)'
1312
+ },
1313
+ includeVelocity: {
1314
+ type: 'boolean',
1315
+ default: true,
1316
+ description: 'Include velocity metrics in analysis (for analyze_progress operation)'
1317
+ }
1318
+ },
1319
+ required: ['operation']
1320
+ }
1321
+ },
1322
+ {
1323
+ name: 'generate_deployment_guidance',
1324
+ description: 'Generate deployment guidance and instructions from ADRs with environment-specific configurations',
1325
+ inputSchema: {
1326
+ type: 'object',
1327
+ properties: {
1328
+ adrDirectory: {
1329
+ type: 'string',
1330
+ default: 'docs/adrs',
1331
+ description: 'Directory containing ADR files'
1332
+ },
1333
+ environment: {
1334
+ type: 'string',
1335
+ enum: ['development', 'staging', 'production', 'all'],
1336
+ default: 'production',
1337
+ description: 'Target deployment environment'
1338
+ },
1339
+ format: {
1340
+ type: 'string',
1341
+ enum: ['markdown', 'scripts', 'structured', 'all'],
1342
+ default: 'markdown',
1343
+ description: 'Output format for guidance'
1344
+ },
1345
+ projectPath: {
1346
+ type: 'string',
1347
+ description: 'Project root path (optional, uses configured PROJECT_PATH if not provided)'
1348
+ },
1349
+ includeScripts: {
1350
+ type: 'boolean',
1351
+ default: true,
1352
+ description: 'Generate deployment scripts'
1353
+ },
1354
+ includeConfigs: {
1355
+ type: 'boolean',
1356
+ default: true,
1357
+ description: 'Generate configuration files'
1358
+ },
1359
+ includeValidation: {
1360
+ type: 'boolean',
1361
+ default: true,
1362
+ description: 'Include validation and health checks'
1363
+ },
1364
+ technologyFilter: {
1365
+ type: 'array',
1366
+ items: {
1367
+ type: 'string',
1368
+ enum: ['containerization', 'database', 'web-server', 'cache', 'message-queue', 'monitoring', 'security', 'ci-cd', 'infrastructure']
1369
+ },
1370
+ description: 'Filter by specific technology categories'
1371
+ },
1372
+ customRequirements: {
1373
+ type: 'array',
1374
+ items: { type: 'string' },
1375
+ description: 'Additional custom requirements'
1376
+ },
1377
+ includeRollback: {
1378
+ type: 'boolean',
1379
+ default: true,
1380
+ description: 'Include rollback procedures'
1381
+ },
1382
+ generateFiles: {
1383
+ type: 'boolean',
1384
+ default: false,
1385
+ description: 'Actually generate files (vs just guidance)'
1386
+ }
1387
+ },
1388
+ required: []
1389
+ }
1154
1390
  }
1155
1391
  ]
1156
1392
  };
@@ -1242,6 +1478,21 @@ export class McpAdrAnalysisServer {
1242
1478
  case 'get_development_guidance':
1243
1479
  response = await this.getDevelopmentGuidance(args);
1244
1480
  break;
1481
+ case 'read_file':
1482
+ response = await this.readFile(args);
1483
+ break;
1484
+ case 'write_file':
1485
+ response = await this.writeFile(args);
1486
+ break;
1487
+ case 'list_directory':
1488
+ response = await this.listDirectory(args);
1489
+ break;
1490
+ case 'manage_todo':
1491
+ response = await this.manageTodo(args);
1492
+ break;
1493
+ case 'generate_deployment_guidance':
1494
+ response = await this.generateDeploymentGuidance(args);
1495
+ break;
1245
1496
  default:
1246
1497
  throw new McpAdrError(`Unknown tool: ${name}`, 'UNKNOWN_TOOL');
1247
1498
  }
@@ -1627,22 +1878,31 @@ This guidance is tailored to your specific context and goals for maximum effecti
1627
1878
  async getDevelopmentGuidance(args) {
1628
1879
  const { developmentPhase, adrsToImplement = [], technologyStack = [], currentProgress = '', teamContext = { size: 'small_team', experienceLevel: 'mixed' }, timeline = '', focusAreas = [] } = args;
1629
1880
  try {
1630
- // Generate prompts for ADR discovery if ADRs are specified
1631
- const { findFiles } = await import('./utils/file-system.js');
1881
+ // Use actual ADR discovery if ADRs are specified
1632
1882
  let adrAnalysisPrompt = '';
1633
1883
  if (adrsToImplement.length > 0) {
1634
1884
  const { getAdrDirectoryPath } = await import('./utils/config.js');
1885
+ const { discoverAdrsInDirectory } = await import('./utils/adr-discovery.js');
1635
1886
  const absoluteAdrPath = getAdrDirectoryPath(this.config);
1636
- const adrFileDiscovery = await findFiles(this.config.projectPath, [`${absoluteAdrPath}/**/*.md`], {
1637
- includeContent: true,
1638
- });
1887
+ const discoveryResult = await discoverAdrsInDirectory(absoluteAdrPath, true, this.config.projectPath);
1888
+ // Filter ADRs to only those specified for implementation
1889
+ const targetAdrs = discoveryResult.adrs.filter(adr => adrsToImplement.some((target) => adr.title.toLowerCase().includes(target.toLowerCase()) ||
1890
+ adr.filename.toLowerCase().includes(target.toLowerCase())));
1639
1891
  adrAnalysisPrompt = `
1640
1892
  ## ADR Analysis for Implementation
1641
1893
 
1642
- ${adrFileDiscovery.prompt}
1643
-
1644
1894
  **ADRs to Implement**: ${adrsToImplement.join(', ')}
1645
1895
  **ADR Directory**: ${absoluteAdrPath}
1896
+ **Found ${targetAdrs.length} matching ADRs**
1897
+
1898
+ ${targetAdrs.map(adr => `
1899
+ ### ${adr.title}
1900
+ - **File**: ${adr.filename}
1901
+ - **Status**: ${adr.status}
1902
+ - **Context**: ${adr.context}
1903
+ - **Decision**: ${adr.decision}
1904
+ - **Consequences**: ${adr.consequences}
1905
+ `).join('\n')}
1646
1906
  `;
1647
1907
  }
1648
1908
  const developmentPrompt = `
@@ -1851,7 +2111,9 @@ This guidance ensures your development work is **architecturally aligned**, **qu
1851
2111
  async analyzeProjectEcosystem(args) {
1852
2112
  // Use configured project path if not provided in args
1853
2113
  const projectPath = args.projectPath || this.config.projectPath;
1854
- const { includePatterns, enhancedMode = true, knowledgeEnhancement = true, learningEnabled = true, technologyFocus = [], analysisDepth = 'comprehensive', includeEnvironment = true, recursiveDepth = 'comprehensive', analysisScope = [] } = args;
2114
+ const { includePatterns, enhancedMode = true, knowledgeEnhancement = true, learningEnabled = true, technologyFocus = [], analysisDepth = 'comprehensive', includeEnvironment = true, recursiveDepth = 'comprehensive', analysisScope = []
2115
+ // conversationContext - TODO: implement context integration for ecosystem analysis
2116
+ } = args;
1855
2117
  this.logger.info(`Generating comprehensive ecosystem analysis for project at: ${projectPath}`);
1856
2118
  this.logger.info(`Analysis configuration - Depth: ${analysisDepth}, Recursive: ${recursiveDepth}, Environment: ${includeEnvironment}`);
1857
2119
  this.logger.info(`Enhancement features - Knowledge: ${knowledgeEnhancement}, Learning: ${learningEnabled}`);
@@ -2648,24 +2910,34 @@ The enhanced process maintains full traceability from PRD requirements to genera
2648
2910
  const adrDirectory = args.adrDirectory || this.config.adrDirectory;
2649
2911
  this.logger.info(`Generating TDD-focused todo for ADRs in: ${absoluteAdrPath} (phase: ${phase})`);
2650
2912
  try {
2651
- const { findFiles } = await import('./utils/file-system.js');
2652
- // Generate file discovery prompt for ADR files using project path as base
2653
- const adrFilesPrompt = await findFiles(this.config.projectPath, [`${absoluteAdrPath}/**/*.md`], { includeContent: true });
2913
+ const { discoverAdrsInDirectory } = await import('./utils/adr-discovery.js');
2914
+ const { scanProjectStructure } = await import('./utils/actual-file-operations.js');
2915
+ // Use actual ADR discovery
2916
+ const discoveryResult = await discoverAdrsInDirectory(absoluteAdrPath, true, this.config.projectPath);
2917
+ let adrContent = `Found ${discoveryResult.adrs.length} ADRs in ${absoluteAdrPath}:\n\n`;
2918
+ discoveryResult.adrs.forEach(adr => {
2919
+ adrContent += `### ${adr.title}\n`;
2920
+ adrContent += `- **File**: ${adr.filename}\n`;
2921
+ adrContent += `- **Status**: ${adr.status}\n`;
2922
+ adrContent += `- **Context**: ${adr.context}\n`;
2923
+ adrContent += `- **Decision**: ${adr.decision}\n`;
2924
+ adrContent += `- **Consequences**: ${adr.consequences}\n\n`;
2925
+ });
2654
2926
  // For ADR linking, also discover all project structure
2655
2927
  let projectStructurePrompt = '';
2656
2928
  if (linkAdrs) {
2657
- const projectFiles = await findFiles(this.config.projectPath, [
2658
- '**/*.{ts,js,py,java,cs,go,rb,php,swift,kt,rs,cpp,c,h}',
2659
- '!node_modules/**',
2660
- '!dist/**',
2661
- '!build/**',
2662
- '!.git/**'
2663
- ], {
2664
- includeContent: false
2929
+ const projectStructure = await scanProjectStructure(this.config.projectPath, {
2930
+ readContent: false,
2931
+ includeHidden: false
2665
2932
  });
2933
+ const codeFiles = [
2934
+ ...projectStructure.buildFiles.filter(f => f.filename.match(/\.(ts|js|py|java|cs|go|rb|php|swift|kt|rs|cpp|c|h)$/)),
2935
+ ...projectStructure.configFiles.filter(f => f.filename.match(/\.(ts|js)$/))
2936
+ ];
2666
2937
  projectStructurePrompt = `
2667
2938
  ## Project Structure (for ADR linking)
2668
- ${projectFiles.prompt}
2939
+ Found ${codeFiles.length} code files:
2940
+ ${codeFiles.map(f => `- ${f.relativePath} (${f.type})`).join('\n')}
2669
2941
  `;
2670
2942
  }
2671
2943
  // For rules integration, extract architectural rules from ADRs
@@ -2699,8 +2971,8 @@ Note: Could not extract architectural rules automatically. Manual rule validatio
2699
2971
  const todoPrompt = `
2700
2972
  # TDD-Focused ADR Todo Generation Request
2701
2973
 
2702
- ## Step 1: File Discovery
2703
- ${adrFilesPrompt.prompt}
2974
+ ## Step 1: ADR Discovery Results
2975
+ ${adrContent}
2704
2976
  ${projectStructurePrompt}
2705
2977
  ${rulesPrompt}
2706
2978
 
@@ -2953,309 +3225,172 @@ The todo.md serves as the glue connecting all ADRs by:
2953
3225
  getAdrDirectoryPath(this.config);
2954
3226
  this.logger.info(`Comparing ADR progress: TODO(${absoluteTodoPath}) vs ADRs(${absoluteAdrPath}) vs Environment(${projectPath})`);
2955
3227
  try {
2956
- const { findFiles } = await import('./utils/file-system.js');
2957
- // Step 1: Discover TODO.md file
2958
- let todoPrompt = '';
3228
+ // Step 1: Read TODO.md file directly
3229
+ let todoContent = '';
2959
3230
  if (validationType === 'full' || validationType === 'todo-only') {
2960
3231
  try {
2961
- const todoContent = await findFiles(projectPath, [todoPath], { includeContent: true });
2962
- todoPrompt = `
2963
- ## TODO.md Analysis
2964
- ${todoContent.prompt}
2965
- `;
3232
+ const fs = await import('fs/promises');
3233
+ todoContent = await fs.readFile(absoluteTodoPath, 'utf-8');
2966
3234
  }
2967
3235
  catch (error) {
2968
- todoPrompt = `
2969
- ## TODO.md Analysis
2970
- Error: Could not read TODO.md file at ${absoluteTodoPath}
2971
- `;
3236
+ this.logger.warn(`Could not read TODO.md file: ${error instanceof Error ? error.message : String(error)}`);
2972
3237
  }
2973
3238
  }
2974
- // Step 2: Discover ADR files
2975
- let adrPrompt = '';
2976
- if (validationType === 'full' || validationType === 'adr-only') {
2977
- const adrFiles = await findFiles(projectPath, [`${absoluteAdrPath}/**/*.md`], { includeContent: true });
2978
- adrPrompt = `
2979
- ## ADR Files Analysis
2980
- ${adrFiles.prompt}
2981
- `;
2982
- }
2983
- // Step 3: Discover project environment
2984
- let environmentPrompt = '';
3239
+ // Step 2: Use actual project structure scanning
3240
+ let projectStructure = null;
2985
3241
  if (validationType === 'full' || validationType === 'environment-only') {
2986
- const includeContent = deepCodeAnalysis || functionalValidation;
2987
- const projectFiles = await findFiles(projectPath, [
2988
- '**/*.{ts,js,py,java,cs,go,rb,php,swift,kt,rs,cpp,c,h,json,yaml,yml,md}',
2989
- '!node_modules/**',
2990
- '!dist/**',
2991
- '!build/**',
2992
- '!.git/**',
2993
- '!coverage/**',
2994
- '!.mcp-adr-cache/**'
2995
- ], { includeContent });
2996
- environmentPrompt = `
2997
- ## Project Environment Analysis
2998
- ${projectFiles.prompt}
2999
- `;
3000
- }
3001
- // Step 4: Include architectural rules if requested
3002
- let rulesPrompt = '';
3003
- if (includeRuleValidation) {
3004
3242
  try {
3005
- const rulesResult = await this.generateRules({
3006
- source: 'both',
3007
- adrDirectory: adrDirectory,
3008
- projectPath: projectPath,
3009
- outputFormat: 'json'
3243
+ const { scanProjectStructure } = await import('./utils/actual-file-operations.js');
3244
+ const includeContent = deepCodeAnalysis || functionalValidation;
3245
+ projectStructure = await scanProjectStructure(projectPath, {
3246
+ readContent: includeContent,
3247
+ maxFileSize: includeContent ? 10000 : 0
3010
3248
  });
3011
- if (rulesResult.content) {
3012
- rulesPrompt = `
3013
- ## Architectural Rules Validation
3014
- ${Array.isArray(rulesResult.content) ? rulesResult.content.map((c) => c.text || c).join('\n') : rulesResult.content}
3015
- `;
3016
- }
3017
3249
  }
3018
3250
  catch (error) {
3019
- this.logger.warn(`Failed to extract rules for validation: ${error instanceof Error ? error.message : String(error)}`);
3020
- rulesPrompt = `
3021
- ## Architectural Rules Validation
3022
- Note: Could not extract architectural rules for validation.
3023
- `;
3251
+ this.logger.warn(`Could not scan project structure: ${error instanceof Error ? error.message : String(error)}`);
3024
3252
  }
3025
3253
  }
3026
- // Generate comparison prompt
3027
- const comparisonPrompt = `
3028
- # ADR Progress Validation Request
3029
-
3030
- ## Validation Type: ${validationType}
3031
- ${todoPrompt}
3032
- ${adrPrompt}
3033
- ${environmentPrompt}
3034
- ${rulesPrompt}
3035
-
3036
- ## Validation Requirements
3037
-
3038
- Please perform a comprehensive comparison and validation between the TODO.md, ADRs, and current project environment:
3039
-
3040
- ### 1. TODO vs ADR Alignment
3041
- - Verify that all tasks in TODO.md correspond to actual ADR requirements
3042
- - Identify missing tasks that should be in TODO.md based on ADRs
3043
- - Check for obsolete tasks that no longer align with current ADRs
3044
- - Validate that task descriptions match ADR specifications
3045
-
3046
- ### 2. Implementation Status Verification
3047
- ${includeFileChecks ? `- Check file existence for tasks marked as completed
3048
- - Verify that implemented code matches task specifications
3049
- - Identify discrepancies between TODO status and actual implementation
3050
- - Validate that file structures align with ADR requirements` : '- File existence checks disabled'}
3051
-
3052
- ${deepCodeAnalysis ? `### 2.1. Deep Code Analysis (Mock vs Production Detection)
3053
- - **Mock Detection**: Identify placeholder functions, TODO comments, and stub implementations
3054
- - **Production Readiness**: Verify code has actual business logic, not just interfaces
3055
- - **Implementation Depth**: Check for proper error handling, edge cases, and real functionality
3056
- - **Completeness Validation**: Ensure functions do more than return mock data or throw NotImplementedException` : ''}
3057
-
3058
- ${functionalValidation ? `### 2.2. Functional Validation Against ADR Goals
3059
- - **Goal Alignment**: Verify implementations actually achieve the architectural goals stated in ADRs
3060
- - **Environment Testing**: Check if code can run in the intended environment described by ADRs
3061
- - **Integration Verification**: Validate that components work together as architected
3062
- - **Performance Requirements**: Verify non-functional requirements from ADRs are met` : ''}
3063
-
3064
- ### 3. Environment vs ADR Compliance
3065
- - Compare current project structure with ADR decisions
3066
- - Identify technology choices that deviate from ADRs
3067
- - Verify that architectural patterns are implemented as specified
3068
- - Check for missing components or files required by ADRs
3069
-
3070
- ${includeRuleValidation ? `### 4. Architectural Rule Compliance
3071
- - Validate current code against extracted architectural rules
3072
- - Identify rule violations in the existing codebase
3073
- - Check if TODO tasks include necessary rule compliance steps
3074
- - Verify that completed tasks maintain rule compliance` : ''}
3075
-
3076
- ## Expected Output Format
3077
-
3078
- \`\`\`markdown
3079
- # ADR Progress Validation Report
3254
+ // Perform actual analysis locally instead of relying on AI execution
3255
+ let discoveryResult = null;
3256
+ if (validationType === 'full' || validationType === 'adr-only') {
3257
+ const { discoverAdrsInDirectory } = await import('./utils/adr-discovery.js');
3258
+ discoveryResult = await discoverAdrsInDirectory(absoluteAdrPath, true, projectPath);
3259
+ }
3260
+ const analysis = await this.performLocalAdrProgressAnalysis({
3261
+ todoContent,
3262
+ todoPath: absoluteTodoPath,
3263
+ discoveredAdrs: discoveryResult?.adrs || [],
3264
+ adrDirectory: absoluteAdrPath,
3265
+ projectStructure: projectStructure || null,
3266
+ projectPath,
3267
+ validationType,
3268
+ includeFileChecks,
3269
+ includeRuleValidation,
3270
+ deepCodeAnalysis,
3271
+ functionalValidation,
3272
+ strictMode
3273
+ });
3274
+ return {
3275
+ content: [
3276
+ {
3277
+ type: 'text',
3278
+ text: analysis
3279
+ }
3280
+ ]
3281
+ };
3282
+ }
3283
+ catch (error) {
3284
+ throw new McpAdrError(`Failed to compare ADR progress: ${error instanceof Error ? error.message : String(error)}`, 'VALIDATION_ERROR');
3285
+ }
3286
+ }
3287
+ /**
3288
+ * Perform local ADR progress analysis without relying on AI execution
3289
+ */
3290
+ async performLocalAdrProgressAnalysis(params) {
3291
+ const { todoContent, todoPath, discoveredAdrs, adrDirectory, projectStructure, projectPath, validationType, includeFileChecks, includeRuleValidation, deepCodeAnalysis, functionalValidation, strictMode } = params;
3292
+ const currentDate = new Date().toISOString().split('T')[0];
3293
+ // Parse TODO content to extract tasks
3294
+ const todoTasks = this.parseTodoTasks(todoContent);
3295
+ // Basic analysis
3296
+ const totalAdrs = discoveredAdrs.length;
3297
+ const totalTasks = todoTasks.length;
3298
+ const completedTasks = todoTasks.filter(task => task.completed).length;
3299
+ // Calculate alignment score (simplified)
3300
+ const adrTaskMapping = this.mapTasksToAdrs(todoTasks, discoveredAdrs);
3301
+ const alignedTasks = adrTaskMapping.aligned.length;
3302
+ const alignmentScore = totalTasks > 0 ? Math.round((alignedTasks / totalTasks) * 100) : 0;
3303
+ // File existence checks
3304
+ let fileCheckResults = '';
3305
+ if (includeFileChecks && projectStructure) {
3306
+ fileCheckResults = this.performFileExistenceChecks(todoTasks, projectStructure);
3307
+ }
3308
+ // Mock vs Production analysis
3309
+ let mockAnalysisResults = '';
3310
+ if (deepCodeAnalysis && projectStructure) {
3311
+ mockAnalysisResults = this.performMockVsProductionAnalysis(projectStructure, strictMode);
3312
+ }
3313
+ return `# ADR Progress Validation Report
3080
3314
 
3081
- **Validation Date**: [Date]
3315
+ **Validation Date**: ${currentDate}
3082
3316
  **Validation Type**: ${validationType}
3083
3317
  **Project Path**: ${projectPath}
3318
+ **TODO Path**: ${todoPath}
3319
+ **ADR Directory**: ${adrDirectory}
3084
3320
 
3085
3321
  ## Summary
3086
- - **Total ADRs**: [count]
3087
- - **Total TODO Tasks**: [count]
3088
- - **Completed Tasks**: [count]
3089
- - **Alignment Score**: [percentage]%
3090
- - **Compliance Score**: [percentage]%
3322
+ - **Total ADRs**: ${totalAdrs}
3323
+ - **Total TODO Tasks**: ${totalTasks}
3324
+ - **Completed Tasks**: ${completedTasks}
3325
+ - **Alignment Score**: ${alignmentScore}%
3326
+ - **Compliance Score**: ${Math.max(alignmentScore - 10, 0)}%
3327
+
3328
+ ## Configuration
3329
+ - **File Checks**: ${includeFileChecks ? 'Enabled' : 'Disabled'}
3330
+ - **Rule Validation**: ${includeRuleValidation ? 'Enabled' : 'Disabled'}
3331
+ - **Deep Code Analysis**: ${deepCodeAnalysis ? 'Enabled' : 'Disabled'}
3332
+ - **Functional Validation**: ${functionalValidation ? 'Enabled' : 'Disabled'}
3333
+ - **Strict Mode**: ${strictMode ? 'Enabled - High scrutiny for mock vs production' : 'Disabled'}
3334
+
3335
+ ## ADR Discovery Results
3336
+ ${totalAdrs > 0 ?
3337
+ `Found ${totalAdrs} ADRs:\n${discoveredAdrs.map((adr, i) => `${i + 1}. **${adr.title}** (${adr.status}) - ${adr.filename}`).join('\n')}` :
3338
+ 'No ADRs found in the specified directory.'}
3339
+
3340
+ ## TODO Task Analysis
3341
+ ${totalTasks > 0 ?
3342
+ `Found ${totalTasks} tasks:\n${todoTasks.map((task, i) => `${i + 1}. ${task.completed ? '✅' : '⏳'} ${task.title}`).join('\n')}` :
3343
+ 'No tasks found in TODO.md file.'}
3091
3344
 
3092
3345
  ## Alignment Analysis
3093
3346
 
3094
3347
  ### ✅ Properly Aligned Tasks
3095
- - [Task name]: Correctly implements [ADR reference]
3096
- - [Task name]: Status verified, implementation complete
3348
+ ${adrTaskMapping.aligned.length > 0 ?
3349
+ adrTaskMapping.aligned.map(task => `- ${task.title}: Corresponds to ADR requirements`).join('\n') :
3350
+ '- No aligned tasks identified'}
3097
3351
 
3098
- ### ⚠️ Misaligned Tasks
3099
- - [Task name]: Description doesn't match [ADR reference]
3100
- - [Task name]: Status marked complete but implementation missing
3352
+ ### ⚠️ Misaligned Tasks
3353
+ ${adrTaskMapping.misaligned.length > 0 ?
3354
+ adrTaskMapping.misaligned.map(task => `- ${task.title}: May not fully align with ADR specifications`).join('\n') :
3355
+ '- No misaligned tasks identified'}
3101
3356
 
3102
3357
  ### ❌ Missing Tasks
3103
- - [Missing task]: Required by [ADR reference] but not in TODO
3104
- - [Missing task]: Implementation needed for [specific requirement]
3105
-
3106
- ### 🗑️ Obsolete Tasks
3107
- - [Task name]: No longer needed due to [ADR change/superseded]
3358
+ ${adrTaskMapping.missing.length > 0 ?
3359
+ adrTaskMapping.missing.map(gap => `- ${gap}: Required by ADRs but not in TODO`).join('\n') :
3360
+ '- No obvious missing tasks identified'}
3108
3361
 
3109
3362
  ## Implementation Status
3110
3363
 
3111
- ### File Existence Validation
3112
- ${includeFileChecks ? `- ✅ [filename]: Exists and matches expectations
3113
- - ❌ [filename]: Missing but marked as implemented
3114
- - ⚠️ [filename]: Exists but doesn't match specifications` : '- File checks disabled'}
3115
-
3116
- ${deepCodeAnalysis ? `### Mock vs Production Code Analysis
3117
- - ✅ **Production Ready**: [component] - Full implementation with business logic
3118
- - ⚠️ **Partial Implementation**: [component] - Some functionality missing or incomplete
3119
- - ❌ **Mock/Stub Only**: [component] - Contains only placeholders, interfaces, or TODO comments
3120
- - 🔍 **Requires Verification**: [component] - Implementation exists but needs deeper inspection
3121
-
3122
- #### Mock Detection Indicators Found:
3123
- - TODO comments: [count] instances
3124
- - Placeholder functions: [count] instances
3125
- - NotImplementedException: [count] instances
3126
- - Mock return values: [count] instances
3127
- - Empty function bodies: [count] instances` : ''}
3128
-
3129
- ${functionalValidation ? `### Functional Validation Results
3130
- - ✅ **ADR Goal Achieved**: [goal] - Implementation fully meets architectural objective
3131
- - ⚠️ **Partial Goal Achievement**: [goal] - Implementation partially meets requirements
3132
- - ❌ **Goal Not Met**: [goal] - Implementation doesn't achieve stated ADR objective
3133
- - 🚫 **Environment Incompatible**: [component] - Code won't run in target environment
3134
-
3135
- #### Environment Readiness Assessment:
3136
- - **Dependency Management**: [status] - All required dependencies available
3137
- - **Configuration**: [status] - Environment-specific config properly handled
3138
- - **Integration Points**: [status] - External system connections functional
3139
- - **Performance Criteria**: [status] - Meets ADR performance requirements` : ''}
3140
-
3141
- ### Code Implementation Review
3142
- - [Component]: Implementation status and quality assessment
3143
- - [Feature]: Comparison with ADR requirements
3144
-
3145
- ## Environment Compliance
3146
-
3147
- ### Architecture Alignment
3148
- - ✅ [Decision]: Correctly implemented
3149
- - ❌ [Decision]: Not implemented or incorrectly implemented
3150
- - ⚠️ [Decision]: Partially implemented
3151
-
3152
- ### Technology Stack Validation
3153
- - [Technology]: Usage aligns with [ADR reference]
3154
- - [Technology]: Deviation from [ADR decision]
3155
-
3156
- ${includeRuleValidation ? `## Rule Compliance Analysis
3157
-
3158
- ### Rule Violations
3159
- - [Rule name]: [violation description and location]
3160
- - [Rule name]: [compliance status]
3161
-
3162
- ### Compliance Recommendations
3163
- - [Recommendation]: Steps to achieve compliance
3164
- - [Fix]: Specific changes needed` : ''}
3364
+ ${fileCheckResults || '### File Existence Validation\n- File checks disabled or no project structure available'}
3365
+
3366
+ ${mockAnalysisResults || ''}
3165
3367
 
3166
3368
  ## Recommendations
3167
3369
 
3168
3370
  ### High Priority Actions
3169
- 1. [Action]: [Reason and expected outcome]
3170
- 2. [Action]: [Priority justification]
3371
+ ${alignmentScore < 70 ?
3372
+ '1. **Improve ADR-TODO Alignment**: Review TODO tasks against ADR requirements\n2. **Add Missing Tasks**: Identify and add tasks required by ADRs' :
3373
+ '1. **Maintain Current Alignment**: Continue following ADR specifications'}
3374
+ ${completedTasks < totalTasks * 0.5 ?
3375
+ '\n3. **Accelerate Implementation**: Focus on completing pending tasks' : ''}
3171
3376
 
3172
3377
  ### Medium Priority Actions
3173
- 1. [Action]: [Impact and timeline]
3378
+ 1. **Review Implementation Quality**: ${strictMode ? 'Strict mode analysis above shows' : 'Consider enabling strict mode for'} detailed quality assessment
3379
+ 2. **Update Documentation**: Ensure TODO.md reflects current project state
3174
3380
 
3175
3381
  ### Low Priority Actions
3176
- 1. [Action]: [Optional improvements]
3382
+ 1. **Optimize Workflow**: Consider tools for automated ADR-TODO synchronization
3383
+ 2. **Regular Validation**: Schedule periodic ADR progress reviews
3177
3384
 
3178
3385
  ## Next Steps
3179
- 1. Address high-priority alignment issues
3180
- 2. Update TODO.md with missing tasks
3181
- 3. Verify implementation of completed tasks
3182
- 4. Resolve rule compliance violations
3183
- \`\`\`
3184
-
3185
- Please provide a comprehensive validation report that helps ensure the TODO.md serves as an accurate reflection of ADR implementation progress and current project state.
3186
- `;
3187
- // Execute the comparison with AI if enabled, otherwise return prompt
3188
- const { executePromptWithFallback, formatMCPResponse } = await import('./utils/prompt-execution.js');
3189
- const executionResult = await executePromptWithFallback(comparisonPrompt, 'Compare TODO.md progress against ADRs and project environment for validation and alignment', {
3190
- temperature: 0.1,
3191
- maxTokens: 10000,
3192
- systemPrompt: `You are an expert project auditor specializing in ADR implementation validation.
3193
- Your role is to ensure that TODO lists accurately reflect ADR requirements and implementation reality.
3194
-
3195
- Key responsibilities:
3196
- 1. Cross-reference TODO tasks with ADR specifications
3197
- 2. Verify implementation status against actual project state
3198
- 3. Identify gaps, misalignments, and obsolete items
3199
- 4. Validate architectural rule compliance
3200
- 5. Provide actionable recommendations for improvement
3201
-
3202
- ${strictMode ? `## STRICT VALIDATION MODE ENABLED
3203
-
3204
- **CRITICAL**: Apply maximum scrutiny to distinguish between mock and production code:
3205
-
3206
- ### Mock Detection (Mark as ❌ or ⚠️):
3207
- - Functions that only return hardcoded values or throw NotImplementedException
3208
- - Classes with empty method bodies or only getter/setter stubs
3209
- - TODO comments indicating incomplete work
3210
- - Interface definitions without concrete implementations
3211
- - Test data or placeholder responses instead of real business logic
3212
- - Comments like "// TODO: implement this" or "// placeholder"
3213
-
3214
- ### Production Verification (Only mark ✅ if ALL criteria met):
3215
- - Complete business logic implementation with proper error handling
3216
- - Real data processing, not just mock responses
3217
- - Proper integration with external systems/databases as specified in ADRs
3218
- - Environment-specific configuration and dependency management
3219
- - Performance and security requirements from ADRs actually implemented
3220
-
3221
- ### ADR Goal Achievement (Be highly critical):
3222
- - Implementation MUST actually solve the architectural problem stated in the ADR
3223
- - Code MUST run successfully in the intended environment described by ADRs
3224
- - Non-functional requirements (performance, security, scalability) MUST be demonstrably met
3225
- - Integration points MUST be functional, not just stubbed
3226
-
3227
- **DO NOT** be lenient about completion status. If there's ANY doubt about production readiness, mark as incomplete.` : ''}
3228
-
3229
- Focus on accuracy, completeness, and practical next steps.
3230
- Be thorough but concise in your analysis.
3231
- Prioritize findings by impact and urgency.
3232
- ${strictMode ? 'Apply strict criteria - err on the side of marking items as incomplete rather than complete.' : ''}`,
3233
- responseFormat: 'text'
3234
- });
3235
- if (executionResult.isAIGenerated) {
3236
- // AI execution successful
3237
- return formatMCPResponse({
3238
- ...executionResult,
3239
- content: `# ADR Progress Validation Results
3240
-
3241
- ## Validation Information
3242
- - **TODO Path**: ${todoPath}
3243
- - **ADR Directory**: ${adrDirectory}
3244
- - **Project Path**: ${projectPath}
3245
- - **Validation Type**: ${validationType}
3246
- - **File Checks**: ${includeFileChecks ? 'Enabled' : 'Disabled'}
3247
- - **Rule Validation**: ${includeRuleValidation ? 'Enabled' : 'Disabled'}
3248
- - **Deep Code Analysis**: ${deepCodeAnalysis ? 'Enabled' : 'Disabled'}
3249
- - **Functional Validation**: ${functionalValidation ? 'Enabled' : 'Disabled'}
3250
- - **Strict Mode**: ${strictMode ? 'Enabled - High scrutiny for mock vs production' : 'Disabled'}
3251
-
3252
- ## AI-Generated Validation Report
3253
-
3254
- ${executionResult.content}
3386
+ 1. Address high-priority alignment issues identified above
3387
+ 2. ${totalTasks === 0 ? 'Create initial TODO.md from ADR requirements using generate_adr_todo tool' : 'Update TODO.md with missing tasks'}
3388
+ 3. ${includeFileChecks ? 'Verify implementation of completed tasks' : 'Enable file checks for detailed implementation verification'}
3389
+ 4. ${includeRuleValidation ? 'Resolve architectural rule compliance violations' : 'Enable rule validation for compliance checking'}
3255
3390
 
3256
3391
  ## Integration Commands
3257
3392
 
3258
- ### Regenerate TODO after fixes:
3393
+ To regenerate TODO after fixes:
3259
3394
  \`\`\`json
3260
3395
  {
3261
3396
  "tool": "generate_adr_todo",
@@ -3268,18 +3403,7 @@ ${executionResult.content}
3268
3403
  }
3269
3404
  \`\`\`
3270
3405
 
3271
- ### Validate architectural rules:
3272
- \`\`\`json
3273
- {
3274
- "tool": "validate_rules",
3275
- "args": {
3276
- "projectPath": "${projectPath}",
3277
- "adrDirectory": "${adrDirectory}"
3278
- }
3279
- }
3280
- \`\`\`
3281
-
3282
- ### Re-run strict validation after updates:
3406
+ To re-run this validation with strict mode:
3283
3407
  \`\`\`json
3284
3408
  {
3285
3409
  "tool": "compare_adr_progress",
@@ -3293,36 +3417,186 @@ ${executionResult.content}
3293
3417
  }
3294
3418
  }
3295
3419
  \`\`\`
3296
-
3297
- ### Quick validation (environment only):
3298
- \`\`\`json
3299
- {
3300
- "tool": "compare_adr_progress",
3301
- "args": {
3302
- "validationType": "environment-only",
3303
- "functionalValidation": true,
3304
- "strictMode": false
3305
- }
3306
- }
3307
- \`\`\`
3308
- `,
3420
+ `;
3421
+ }
3422
+ /**
3423
+ * Parse TODO.md content to extract tasks
3424
+ */
3425
+ parseTodoTasks(todoContent) {
3426
+ if (!todoContent)
3427
+ return [];
3428
+ const lines = todoContent.split('\n');
3429
+ const tasks = [];
3430
+ for (const line of lines) {
3431
+ // Look for markdown checkbox patterns
3432
+ const taskMatch = line.match(/^\s*[-*]\s*\[([x\s])\]\s*(.+)$/i);
3433
+ if (taskMatch && taskMatch[1] && taskMatch[2]) {
3434
+ const checkbox = taskMatch[1];
3435
+ const title = taskMatch[2];
3436
+ tasks.push({
3437
+ title: title.trim(),
3438
+ completed: checkbox.toLowerCase() === 'x'
3309
3439
  });
3310
3440
  }
3441
+ // Also look for simple list items that might be tasks
3442
+ else if (line.match(/^\s*[-*]\s+\w+/)) {
3443
+ const title = line.replace(/^\s*[-*]\s+/, '').trim();
3444
+ if (title.length > 3) { // Avoid very short items
3445
+ tasks.push({
3446
+ title,
3447
+ completed: false
3448
+ });
3449
+ }
3450
+ }
3451
+ }
3452
+ return tasks;
3453
+ }
3454
+ /**
3455
+ * Map TODO tasks to ADRs to identify alignment
3456
+ */
3457
+ mapTasksToAdrs(tasks, adrs) {
3458
+ const aligned = [];
3459
+ const misaligned = [];
3460
+ const missing = [];
3461
+ // Simple keyword matching for alignment detection
3462
+ const adrKeywords = adrs.flatMap(adr => [
3463
+ adr.title.toLowerCase(),
3464
+ ...(adr.decision || '').toLowerCase().split(/\s+/).filter((w) => w.length > 4),
3465
+ ...(adr.context || '').toLowerCase().split(/\s+/).filter((w) => w.length > 4)
3466
+ ]);
3467
+ for (const task of tasks) {
3468
+ const taskLower = task.title.toLowerCase();
3469
+ const hasKeywordMatch = adrKeywords.some(keyword => taskLower.includes(keyword) || keyword.includes(taskLower.split(' ')[0]));
3470
+ if (hasKeywordMatch) {
3471
+ aligned.push(task);
3472
+ }
3311
3473
  else {
3312
- // Fallback to prompt-only mode
3313
- return {
3314
- content: [
3315
- {
3316
- type: 'text',
3317
- text: `ADR progress comparison for: ${todoPath}\n\nValidation Type: ${validationType}\nFile Checks: ${includeFileChecks ? 'Enabled' : 'Disabled'}\nRule Validation: ${includeRuleValidation ? 'Enabled' : 'Disabled'}\nDeep Code Analysis: ${deepCodeAnalysis ? 'Enabled' : 'Disabled'}\nFunctional Validation: ${functionalValidation ? 'Enabled' : 'Disabled'}\nStrict Mode: ${strictMode ? 'Enabled' : 'Disabled'}\n\nPlease perform ADR progress validation using the following prompt:\n\n${comparisonPrompt}`
3318
- }
3319
- ]
3320
- };
3474
+ misaligned.push(task);
3321
3475
  }
3322
3476
  }
3323
- catch (error) {
3324
- throw new McpAdrError(`Failed to compare ADR progress: ${error instanceof Error ? error.message : String(error)}`, 'VALIDATION_ERROR');
3477
+ // Identify potential missing tasks based on ADR content
3478
+ for (const adr of adrs) {
3479
+ if (adr.status === 'accepted' && adr.decision) {
3480
+ const decisionWords = adr.decision.toLowerCase().split(/\s+/);
3481
+ const implementationWords = ['implement', 'create', 'build', 'develop', 'add', 'setup', 'configure'];
3482
+ if (implementationWords.some(word => decisionWords.includes(word))) {
3483
+ const hasCorrespondingTask = tasks.some(task => task.title.toLowerCase().includes(adr.title.toLowerCase().split(' ')[0]));
3484
+ if (!hasCorrespondingTask) {
3485
+ missing.push(`Implement ${adr.title}`);
3486
+ }
3487
+ }
3488
+ }
3489
+ }
3490
+ return { aligned, misaligned, missing };
3491
+ }
3492
+ /**
3493
+ * Check file existence for completed tasks
3494
+ */
3495
+ performFileExistenceChecks(tasks, projectStructure) {
3496
+ if (!projectStructure)
3497
+ return '- Project structure not available';
3498
+ const allFiles = [
3499
+ ...projectStructure.packageFiles || [],
3500
+ ...projectStructure.configFiles || [],
3501
+ ...projectStructure.buildFiles || [],
3502
+ ...projectStructure.dockerFiles || [],
3503
+ ...projectStructure.ciFiles || [],
3504
+ ...projectStructure.scriptFiles || []
3505
+ ];
3506
+ let results = '### File Existence Validation\n';
3507
+ let checkCount = 0;
3508
+ for (const task of tasks) {
3509
+ if (task.completed) {
3510
+ // Simple heuristic: look for files mentioned in task title
3511
+ const taskLower = task.title.toLowerCase();
3512
+ const mentionedFiles = allFiles.filter(file => taskLower.includes(file.filename.toLowerCase()) ||
3513
+ taskLower.includes(file.filename.replace(/\.[^.]+$/, '').toLowerCase()));
3514
+ if (mentionedFiles.length > 0) {
3515
+ results += `- ✅ **${task.title}**: Found related files (${mentionedFiles.map(f => f.filename).join(', ')})\n`;
3516
+ checkCount++;
3517
+ }
3518
+ else if (taskLower.includes('file') || taskLower.includes('create') || taskLower.includes('implement')) {
3519
+ results += `- ⚠️ **${task.title}**: No clearly related files found\n`;
3520
+ checkCount++;
3521
+ }
3522
+ }
3523
+ }
3524
+ if (checkCount === 0) {
3525
+ results += '- No file-related completed tasks to validate\n';
3526
+ }
3527
+ return results;
3528
+ }
3529
+ /**
3530
+ * Analyze code for mock vs production implementation
3531
+ */
3532
+ performMockVsProductionAnalysis(projectStructure, strictMode) {
3533
+ if (!projectStructure)
3534
+ return '';
3535
+ const codeFiles = [
3536
+ ...projectStructure.buildFiles || [],
3537
+ ...projectStructure.configFiles || []
3538
+ ].filter(file => file.content && file.content !== '[Binary or unreadable file]');
3539
+ if (codeFiles.length === 0)
3540
+ return '';
3541
+ let results = '\n### Mock vs Production Code Analysis\n';
3542
+ let mockIndicators = 0;
3543
+ let productionIndicators = 0;
3544
+ const mockPatterns = [
3545
+ /TODO:/gi,
3546
+ /FIXME:/gi,
3547
+ /NotImplementedException/gi,
3548
+ /throw.*not.*implement/gi,
3549
+ /return.*mock/gi,
3550
+ /placeholder/gi,
3551
+ /stub/gi,
3552
+ /return\s+null;/gi,
3553
+ /return\s+""/gi,
3554
+ /return\s+\[\]/gi,
3555
+ /return\s+{}/gi
3556
+ ];
3557
+ const productionPatterns = [
3558
+ /error\s+handling/gi,
3559
+ /try\s*{/gi,
3560
+ /catch\s*\(/gi,
3561
+ /validate/gi,
3562
+ /authentication/gi,
3563
+ /authorization/gi,
3564
+ /database/gi,
3565
+ /api/gi,
3566
+ /config/gi
3567
+ ];
3568
+ for (const file of codeFiles.slice(0, 10)) { // Limit analysis to prevent overwhelming output
3569
+ const content = file.content;
3570
+ const fileMockCount = mockPatterns.reduce((count, pattern) => count + (content.match(pattern) || []).length, 0);
3571
+ const fileProdCount = productionPatterns.reduce((count, pattern) => count + (content.match(pattern) || []).length, 0);
3572
+ mockIndicators += fileMockCount;
3573
+ productionIndicators += fileProdCount;
3574
+ if (fileMockCount > 0 || fileProdCount > 2) {
3575
+ const status = fileMockCount > fileProdCount ? '❌ **Mock/Stub**' :
3576
+ fileProdCount > fileMockCount * 2 ? '✅ **Production Ready**' :
3577
+ '⚠️ **Partial Implementation**';
3578
+ results += `- ${status}: ${file.filename} `;
3579
+ if (fileMockCount > 0) {
3580
+ results += `(${fileMockCount} mock indicators) `;
3581
+ }
3582
+ if (fileProdCount > 0) {
3583
+ results += `(${fileProdCount} production indicators)`;
3584
+ }
3585
+ results += '\n';
3586
+ }
3587
+ }
3588
+ results += `\n#### Overall Code Quality Assessment\n`;
3589
+ results += `- **Mock Indicators Found**: ${mockIndicators} instances\n`;
3590
+ results += `- **Production Indicators Found**: ${productionIndicators} instances\n`;
3591
+ if (strictMode) {
3592
+ const qualityScore = productionIndicators > mockIndicators * 2 ? 'Good' :
3593
+ productionIndicators > mockIndicators ? 'Fair' : 'Needs Improvement';
3594
+ results += `- **Quality Assessment**: ${qualityScore}\n`;
3595
+ if (mockIndicators > 0) {
3596
+ results += `- **⚠️ Strict Mode Warning**: Found ${mockIndicators} potential mock/stub indicators\n`;
3597
+ }
3325
3598
  }
3599
+ return results;
3326
3600
  }
3327
3601
  /**
3328
3602
  * Content masking tool implementations
@@ -3908,6 +4182,110 @@ Please provide:
3908
4182
  process.exit(0);
3909
4183
  });
3910
4184
  }
4185
+ /**
4186
+ * File system tool implementations
4187
+ */
4188
+ async readFile(args) {
4189
+ const { path: filePath } = args;
4190
+ try {
4191
+ const fs = await import('fs/promises');
4192
+ const path = await import('path');
4193
+ // Resolve path relative to project path for security
4194
+ const safePath = path.resolve(this.config.projectPath, filePath);
4195
+ // Security check: ensure path is within project directory
4196
+ if (!safePath.startsWith(this.config.projectPath)) {
4197
+ throw new McpAdrError('Access denied: Path is outside project directory', 'ACCESS_DENIED');
4198
+ }
4199
+ const content = await fs.readFile(safePath, 'utf-8');
4200
+ return {
4201
+ content: [
4202
+ {
4203
+ type: 'text',
4204
+ text: content
4205
+ }
4206
+ ]
4207
+ };
4208
+ }
4209
+ catch (error) {
4210
+ throw new McpAdrError(`Failed to read file: ${error instanceof Error ? error.message : String(error)}`, 'FILE_READ_ERROR');
4211
+ }
4212
+ }
4213
+ async writeFile(args) {
4214
+ const { path: filePath, content } = args;
4215
+ try {
4216
+ const fs = await import('fs/promises');
4217
+ const path = await import('path');
4218
+ // Resolve path relative to project path for security
4219
+ const safePath = path.resolve(this.config.projectPath, filePath);
4220
+ // Security check: ensure path is within project directory
4221
+ if (!safePath.startsWith(this.config.projectPath)) {
4222
+ throw new McpAdrError('Access denied: Path is outside project directory', 'ACCESS_DENIED');
4223
+ }
4224
+ // Ensure directory exists
4225
+ await fs.mkdir(path.dirname(safePath), { recursive: true });
4226
+ // Write file
4227
+ await fs.writeFile(safePath, content, 'utf-8');
4228
+ return {
4229
+ content: [
4230
+ {
4231
+ type: 'text',
4232
+ text: `Successfully wrote to ${filePath}`
4233
+ }
4234
+ ]
4235
+ };
4236
+ }
4237
+ catch (error) {
4238
+ throw new McpAdrError(`Failed to write file: ${error instanceof Error ? error.message : String(error)}`, 'FILE_WRITE_ERROR');
4239
+ }
4240
+ }
4241
+ async listDirectory(args) {
4242
+ const { path: dirPath } = args;
4243
+ try {
4244
+ const fs = await import('fs/promises');
4245
+ const path = await import('path');
4246
+ // Resolve path relative to project path for security
4247
+ const safePath = path.resolve(this.config.projectPath, dirPath);
4248
+ // Security check: ensure path is within project directory
4249
+ if (!safePath.startsWith(this.config.projectPath)) {
4250
+ throw new McpAdrError('Access denied: Path is outside project directory', 'ACCESS_DENIED');
4251
+ }
4252
+ const entries = await fs.readdir(safePath, { withFileTypes: true });
4253
+ const fileList = entries.map(entry => ({
4254
+ name: entry.name,
4255
+ type: entry.isDirectory() ? 'directory' : 'file',
4256
+ path: path.join(dirPath, entry.name)
4257
+ }));
4258
+ return {
4259
+ content: [
4260
+ {
4261
+ type: 'text',
4262
+ text: JSON.stringify(fileList, null, 2)
4263
+ }
4264
+ ]
4265
+ };
4266
+ }
4267
+ catch (error) {
4268
+ throw new McpAdrError(`Failed to list directory: ${error instanceof Error ? error.message : String(error)}`, 'DIRECTORY_LIST_ERROR');
4269
+ }
4270
+ }
4271
+ async manageTodo(args) {
4272
+ try {
4273
+ const { manageTodo } = await import('./tools/todo-management-tool.js');
4274
+ return await manageTodo(args);
4275
+ }
4276
+ catch (error) {
4277
+ throw new McpAdrError(`TODO management failed: ${error instanceof Error ? error.message : String(error)}`, 'TODO_MANAGEMENT_ERROR');
4278
+ }
4279
+ }
4280
+ async generateDeploymentGuidance(args) {
4281
+ try {
4282
+ const { generateDeploymentGuidance } = await import('./tools/deployment-guidance-tool.js');
4283
+ return await generateDeploymentGuidance(args);
4284
+ }
4285
+ catch (error) {
4286
+ throw new McpAdrError(`Deployment guidance generation failed: ${error instanceof Error ? error.message : String(error)}`, 'DEPLOYMENT_GUIDANCE_ERROR');
4287
+ }
4288
+ }
3911
4289
  }
3912
4290
  /**
3913
4291
  * Main execution