Files
makemd/scripts/sync-check.js

249 lines
6.7 KiB
JavaScript
Raw Permalink Normal View History

#!/usr/bin/env node
/**
* 🔄 代码-看板同步检查脚本 (Node.js版本)
* 用途自动检查服务类实现与协作看板任务的同步状态
*/
const fs = require('fs');
const path = require('path');
const { execSync } = require('child_process');
// 配置参数
const SERVICES_DIR = 'server/src/services';
const BOARD_FILE = 'docs/08-governance/collaboration-board.md';
const REPORT_FILE = 'docs/sync-status-report.md';
// 颜色定义
const colors = {
red: '\x1b[31m',
green: '\x1b[32m',
yellow: '\x1b[33m',
blue: '\x1b[34m',
reset: '\x1b[0m'
};
function log(message, color = 'reset') {
console.log(`${colors[color]}${message}${colors.reset}`);
}
function findServiceFiles() {
const servicesPath = path.join(__dirname, '..', SERVICES_DIR);
const files = [];
function scanDirectory(dir) {
const items = fs.readdirSync(dir);
for (const item of items) {
const fullPath = path.join(dir, item);
const stat = fs.statSync(fullPath);
if (stat.isDirectory()) {
scanDirectory(fullPath);
} else if (item.endsWith('Service.ts')) {
files.push(fullPath);
}
}
}
scanDirectory(servicesPath);
return files;
}
function extractServiceClasses(files) {
const services = [];
for (const file of files) {
const content = fs.readFileSync(file, 'utf8');
const serviceMatch = content.match(/export class (\w+Service)/);
if (serviceMatch) {
services.push(serviceMatch[1]);
}
}
return services.sort();
}
function extractBoardTasks() {
const boardContent = fs.readFileSync(BOARD_FILE, 'utf8');
// 改进的任务提取正则表达式
// 匹配格式: [TASK_ID] 描述文字 (ServiceName)
const taskRegex = /\[([A-Z_0-9]+)\][^\n]*\(([A-Za-z]+Service)\)/g;
const tasks = [];
let match;
while ((match = taskRegex.exec(boardContent)) !== null) {
// 同时提取任务ID和服务名
const taskId = match[1];
const serviceName = match[2];
tasks.push({ taskId, serviceName });
}
// 返回服务名列表
return [...new Set(tasks.map(t => t.serviceName))].sort();
}
function generateSyncReport(services, tasks) {
const missingTasks = services.filter(service => !tasks.includes(service));
const extraTasks = tasks.filter(task => !services.includes(task));
const serviceCount = services.length;
const taskCount = tasks.length;
const missingCount = missingTasks.length;
const extraCount = extraTasks.length;
const coverage = serviceCount > 0 ? Math.round((serviceCount - missingCount) * 100 / serviceCount) : 0;
// 生成报告内容
const reportContent = `# 📊 代码-看板同步状态报告
> **生成时间**: ${new Date().toLocaleString('zh-CN')}
> **检查范围**: 服务类实现与协作看板任务同步状态
---
## 📋 同步概览
| 指标 | 数量 | 状态 |
|------|------|------|
| 服务类总数 | ${serviceCount} | |
| 看板任务数 | ${taskCount} | |
| 遗漏任务数 | ${missingCount} | ${missingCount === 0 ? '✅' : '❌'} |
| 多余任务数 | ${extraCount} | ${extraCount === 0 ? '✅' : '❌'} |
| 同步覆盖率 | ${coverage}% | ${missingCount === 0 ? '✅' : '⚠️'} |
---
## 🔍 详细分析
${missingCount > 0 ? `### ❌ 遗漏任务 (${missingCount} 个)
以下服务类已实现但未在协作看板中
${missingTasks.map(task => `- ${task}`).join('\n')}
` : '### ✅ 无遗漏任务'}
${extraCount > 0 ? `### ⚠️ 多余任务 (${extraCount} 个)
以下任务在看板中存在但代码未实现
${extraTasks.map(task => `- ${task}`).join('\n')}
` : '### ✅ 无多余任务'}
---
## 🚀 同步建议
### 立即行动
${missingCount > 0 ? '1. **补充遗漏任务**:将遗漏的服务类添加到协作看板\n' : ''}${extraCount > 0 ? '2. **清理多余任务**:删除或标记未实现的任务\n' : ''}
### 长期优化
1. **建立同步机制**每次代码提交后自动检查同步状态
2. **定期审查**每周执行一次全面同步检查
3. **自动化工具**开发更智能的同步检查工具
---
## 📈 同步健康度
**总体同步状态**: ${missingCount === 0 && extraCount === 0 ? '✅ 优秀' : missingCount <= 3 && extraCount <= 3 ? '⚠️ 良好' : '❌ 需要改进'}
**建议优先级**: ${missingCount > 5 ? '高' : missingCount > 2 ? '中' : '低'}
---
## 🔧 使用说明
### 手动运行
\`\`\`bash
node scripts/sync-check.js
\`\`\`
### 集成到 CI/CD
\`\`\`yaml
# CI 配置中添加
- name: 代码-看板同步检查
run: node scripts/sync-check.js
\`\`\`
### 定期检查
建议每周运行一次确保代码与看板保持同步
`;
return {
serviceCount,
taskCount,
missingCount,
extraCount,
coverage,
missingTasks,
extraTasks,
reportContent
};
}
function main() {
log('🔍 开始代码-看板同步检查...', 'blue');
log('==========================================', 'blue');
try {
// 1. 扫描所有服务类
const serviceFiles = findServiceFiles();
const services = extractServiceClasses(serviceFiles);
log(`✅ 发现 ${services.length} 个服务类`, 'green');
// 2. 从看板提取任务列表
const tasks = extractBoardTasks();
log(`✅ 发现 ${tasks.length} 个看板任务`, 'green');
// 3. 生成同步报告
const report = generateSyncReport(services, tasks);
// 4. 保存报告
fs.writeFileSync(REPORT_FILE, report.reportContent);
// 5. 输出结果
log('==========================================', 'blue');
log('✅ 同步检查完成!', 'green');
log(`📊 报告位置: ${REPORT_FILE}`, 'blue');
if (report.missingCount > 0) {
log(`❌ 发现 ${report.missingCount} 个遗漏任务:`, 'red');
report.missingTasks.forEach(task => log(` - ${task}`, 'red'));
} else {
log('✅ 无遗漏任务', 'green');
}
if (report.extraCount > 0) {
log(`⚠️ 发现 ${report.extraCount} 个多余任务:`, 'yellow');
report.extraTasks.forEach(task => log(` - ${task}`, 'yellow'));
} else {
log('✅ 无多余任务', 'green');
}
// 6. 显示同步状态摘要
if (report.missingCount === 0 && report.extraCount === 0) {
log('🎉 完美同步!代码与看板完全一致', 'green');
} else if (report.missingCount <= 3 && report.extraCount <= 3) {
log('⚠️ 同步良好,有少量差异需要处理', 'yellow');
} else {
log('❌ 同步问题严重,需要立即处理', 'red');
}
} catch (error) {
log(`❌ 同步检查失败: ${error.message}`, 'red');
process.exit(1);
}
}
// 如果是直接运行此文件
if (require.main === module) {
main();
}
module.exports = {
findServiceFiles,
extractServiceClasses,
extractBoardTasks,
generateSyncReport
};