diff --git a/.github/workflows/notion-callback-pipeline.yml b/.github/workflows/notion-callback-pipeline.yml index 6be491f6..a6fc2d39 100644 --- a/.github/workflows/notion-callback-pipeline.yml +++ b/.github/workflows/notion-callback-pipeline.yml @@ -208,31 +208,38 @@ jobs: const status = process.env.NOTION_STATUS || 'unknown'; const now = new Date().toISOString(); - // 检查是否已存在相同事件 - const exists = memory.events.some(function(e) { + // 检查是否已存在相同事件(按 broadcast_id 精确匹配 + 同类型 + 同日期) + const eventKey = 'Notion 回传核验 · ' + broadcastId; + const todayStr = now.slice(0, 10); + const existingIdx = memory.events.findIndex(function(e) { return e.type === 'notion_callback' && - e.description && e.description.includes(broadcastId) && - e.date === now.slice(0, 10); + e.broadcast_id === broadcastId && + e.date === todayStr; }); - if (!exists) { - memory.events.unshift({ - date: now.slice(0, 10), - type: 'notion_callback', - description: 'Notion 回传核验 · ' + broadcastId + ' · 状态: ' + status, - by: '铸渊Agent·Notion回传管道' - }); + const newEvent = { + date: todayStr, + type: 'notion_callback', + broadcast_id: broadcastId, + description: eventKey + ' · 状态: ' + status, + by: '铸渊Agent·Notion回传管道' + }; - // 保留最近 20 条事件 - if (memory.events.length > 20) { - memory.events = memory.events.slice(0, 20); - } - - fs.writeFileSync(memoryPath, JSON.stringify(memory, null, 2) + '\n'); - console.log('✅ 大脑记忆已更新'); + if (existingIdx >= 0) { + // 同一 broadcast_id 只保留最新的一条 + memory.events[existingIdx] = newEvent; + console.log('ℹ️ 已更新同日同广播事件'); } else { - console.log('ℹ️ 事件已存在,跳过'); + memory.events.unshift(newEvent); } + + // 保留最近 20 条事件 + if (memory.events.length > 20) { + memory.events = memory.events.slice(0, 20); + } + + fs.writeFileSync(memoryPath, JSON.stringify(memory, null, 2) + '\n'); + console.log('✅ 大脑记忆已更新'); " env: BROADCAST_ID: ${{ steps.callback.outputs.broadcast_id }} diff --git a/.github/workflows/syslog-auto-pipeline.yml b/.github/workflows/syslog-auto-pipeline.yml index 1344c3e2..02eb3e5e 100644 --- a/.github/workflows/syslog-auto-pipeline.yml +++ b/.github/workflows/syslog-auto-pipeline.yml @@ -177,13 +177,17 @@ jobs: '验证详情: ' + moduleVerify.slice(0, 400), ].join('\\n'); + // SYSLOG类型工单设为'待处理'(等待Notion侧核心大脑处理) + // 提问类型工单设为'已完成'(铸渊已生成解答) + const ticketStatus = type === 'syslog' ? '待处理' : '已完成'; + const body = JSON.stringify({ parent: { database_id: dbId }, properties: { '标题': { title: [{ type: 'text', text: { content: title.slice(0, 120) } }] }, '操作类型': { select: { name: '其他' } }, '提交者': { rich_text: [{ type: 'text', text: { content: '铸渊Agent·自动管道' } }] }, - '状态': { select: { name: '待处理' } }, + '状态': { select: { name: ticketStatus } }, '优先级': { select: { name: 'P1' } } }, children: [{ diff --git a/.github/workflows/syslog-issue-pipeline.yml b/.github/workflows/syslog-issue-pipeline.yml index de09bac0..4acbc3b0 100644 --- a/.github/workflows/syslog-issue-pipeline.yml +++ b/.github/workflows/syslog-issue-pipeline.yml @@ -177,13 +177,17 @@ jobs: '验证详情: ' + moduleVerify.slice(0, 400), ].join('\\n'); + // SYSLOG类型工单设为'待处理'(等待Notion侧核心大脑处理) + // 提问类型工单设为'已完成'(铸渊已生成解答) + const ticketStatus = type === 'syslog' ? '待处理' : '已完成'; + const body = JSON.stringify({ parent: { database_id: dbId }, properties: { '标题': { title: [{ type: 'text', text: { content: title.slice(0, 120) } }] }, '操作类型': { select: { name: '其他' } }, '提交者': { rich_text: [{ type: 'text', text: { content: '铸渊Agent·自动管道' } }] }, - '状态': { select: { name: '待处理' } }, + '状态': { select: { name: ticketStatus } }, '优先级': { select: { name: 'P1' } } }, children: [{ diff --git a/scripts/verify-modules.js b/scripts/verify-modules.js index 807ec605..2df4ddf5 100644 --- a/scripts/verify-modules.js +++ b/scripts/verify-modules.js @@ -63,23 +63,32 @@ function extractModuleIds(content, broadcastId) { // ══════════════════════════════════════════════════════════ function extractDevId(content, broadcastId) { - // 从广播编号提取开发者后缀(如 BC-M22-009-AW → AW) - var suffixMatch = broadcastId.match(/BC-[A-Z0-9]+-\d+-([A-Z]+)/i); - var devSuffix = suffixMatch ? suffixMatch[1] : ''; - - // 从内容中提取 DEV-XXX + // 从内容中直接提取 DEV-XXX(最优先) var devMatch = content.match(/\b(DEV-\d{3})\b/i); if (devMatch) return devMatch[1].toUpperCase(); - // 从 dev-status.json 通过后缀查找 + // 从广播编号提取开发者后缀(如 BC-M22-009-AW → AW) + var suffixMatch = broadcastId.match(/BC-[A-Z0-9]+-\d+-([A-Z]+)/i); + var devSuffix = suffixMatch ? suffixMatch[1].toUpperCase() : ''; + + // 从 dev-status.json 通过后缀匹配开发者 if (devSuffix) { try { var devStatus = JSON.parse(fs.readFileSync(DEV_STATUS_PATH, 'utf8')); var team = devStatus.team || []; + // 后缀缩写映射表(从 dev-status.json 中名字的拼音首字母) + var suffixMap = { + 'YY': 'DEV-001', 'FM': 'DEV-002', 'YF': 'DEV-003', + 'ZZ': 'DEV-004', 'XCM': 'DEV-005', 'HE': 'DEV-009', + 'JZ': 'DEV-010', 'CCNN': 'DEV-011', 'AW': 'DEV-012', + 'XX': 'DEV-013', 'SY': 'DEV-014', + }; + if (suffixMap[devSuffix]) return suffixMap[devSuffix]; + + // 兜底:尝试从 team 中匹配 waiting 字段里的广播编号 for (var i = 0; i < team.length; i++) { - var name = team[i].name || ''; - // 简单匹配:用名字首字母缩写匹配后缀 - if (name && devSuffix.length >= 2) { + var waiting = team[i].waiting || ''; + if (waiting.includes(broadcastId) || waiting.includes(devSuffix)) { return team[i].dev_id; } }