@ghyper9023/pi-dev-workflow 0.3.3 → 0.4.1

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.
@@ -0,0 +1,14 @@
1
+ [fix] 修复 extensions/workflow-engine.ts 1179行的let agentResult = await runAgentWithProgress(loopAgent, loopTask, stepIndex, step.loopAgentName!, step.timeoutMs);和1432行-1435行的 sendWorkflowResult(pi, finalState, prompt, _workflowType); // Cleanup widget after delay setTimeout(() => cleanupWidget(), 5000); 中的 1179行:executeLoopGroup 函数在调用 runAgentWithProgress 后没有检查 agentResult.exitCode。如果 sub-agent 进程非正常退出(例如崩溃或报错),工作流会忽略该错误并继续尝试运行 Reviewer。建议检查退出码,并在失败时抛出异常或中断循环。1432行:使用 setTimeout 延迟 5 秒执行 cleanupWidget 存在竞态风险。如果用户在工作流完成后 5 秒内立即启动了一个新的工作流,这个定时器触发时会调用 cleanupWidget 并将全局变量 _workflowRunning 重置为 false,从而干扰甚至中断正在运行的新工作流。建议通过对比工作流启动时间戳或在启动新工作流时显式取消之前的定时器来解决。
2
+
3
+ **背景**:
4
+ - 输入:见代码上下文
5
+ - 预期行为:修复问题,但不能破坏原因功能结构和其他代码
6
+ - 当前错误:请描述当前错误
7
+ **任务**:
8
+ 1. 不要仅仅消除报错(Suppress),要解决根本原因。
9
+ 2. 先读取相关代码和日志,诊断根因(多步推理,不要先给结论)。
10
+ 3. 提供至少一种修复方案,并说明为什么这样做。
11
+ 4. 编写测试用例复现该 Bug 并确认修复有效。
12
+ **输出**:提供 diff 和两句话的根因分析。
13
+ **约束**:只修 bug,不做重构;最小化改动;不要假设错误是微不足道的。
14
+ **验证**:运行 tests通过 确认修复。
@@ -0,0 +1,150 @@
1
+ # 修复 workflow-engine 中两个 Bug — 实施计划
2
+
3
+ ## 概述
4
+
5
+ 修复 `extensions/workflow-engine.ts` 中的两个 Bug:
6
+
7
+ 1. **Bug A — executeLoopGroup 缺少 exitCode 检查**(第 1179 行):`executeLoopGroup` 函数在调用 `runAgentWithProgress` 后,只处理了超时(`isTimeoutResult`),但没有检查 sub-agent 非正常退出(exitCode !== 0 且 exitCode !== -1)的情况。对比 `executeSingleStep` 在第 1146 行有显式的 exitCode 检查。这会导致 agent 崩溃或报错时,工作流继续运行 reviewer,产生错误的结果。
8
+
9
+ 2. **Bug B — setTimeout cleanupWidget 竞态条件**(第 1436 行和第 1648 行):工作流完成或取消后,使用 `setTimeout(() => cleanupWidget(), 5000)` 延迟 5 秒清理 widget。如果用户在这 5 秒内启动新工作流,定时器触发时会调用 `cleanupWidget`,将 `_workflowRunning` 设为 `false` 并清空 `_lastWorkflowCtx`,破坏正在运行的新工作流。
10
+
11
+ ## 根因分析
12
+
13
+ **Bug A 根因**:`executeLoopGroup` 在 2025 年 3 月的迭代中从 `executeSingleStep` 分支出来,当时只实现了超时处理逻辑(`isTimeoutResult`),但遗漏了通用的 exitCode 非零检查。`executeSingleStep` 在第 1146 行有 `if (result.exitCode !== 0 && result.stderr) { throw new Error(...); }`,但 `executeLoopGroup` 中没有对应逻辑。
14
+
15
+ **Bug B 根因**:使用延迟 `setTimeout` 进行异步清理是一种脆弱的模式。它假设在定时器超时前不会有新的工作流启动,但用户可能在完成消息查看后立即开始新的工作流。`cleanupWidget` 会无条件重置 `_workflowRunning` 和 `_lastWorkflowCtx` 等全局状态,没有任何保护机制。
16
+
17
+ ## 文件清单
18
+
19
+ ### 修改文件
20
+ | 文件路径 | 改动描述 | 风险等级 |
21
+ |---------|---------|---------|
22
+ | `extensions/workflow-engine.ts` | 修复 Bug A(添加 exitCode 检查)和 Bug B(定时器竞态保护) | 低 |
23
+
24
+ ### 新增文件
25
+ | 文件路径 | 用途说明 |
26
+ |---------|---------|
27
+ | `tests/test-workflow-engine-bugs.mjs` | 复现并验证 Bug A 和 Bug B 的修复 |
28
+
29
+ ## 实施步骤
30
+
31
+ ### 步骤 1:修复 executeLoopGroup 缺少 exitCode 检查(Bug A)
32
+
33
+ - **前置条件**:无
34
+ - **改动文件**:`extensions/workflow-engine.ts`
35
+ - **改动位置**:第 1179 行 `let agentResult = await runAgentWithProgress(...)` 之后
36
+ - **改动内容**:在 `isTimeoutResult(agentResult)` 判断之前,插入 exitCode 检查。如果 `agentResult.exitCode !== 0` 且 `agentResult.exitCode !== -1`(-1 是超时标记),则根据 mode 分支处理:
37
+ - **full-auto 模式**:直接 `throw new Error(...)`,由上层 `executeWorkflowBackground` 的 catch 块捕获,将步骤标记为 failed。
38
+ - **非 full-auto 模式**:弹出 UI 选择,让用户选择"重新执行"、"跳过此步骤"或"取消工作流"(与超时处理的分支逻辑一致)。
39
+
40
+ 具体代码片段(在 `isTimeoutResult` 检查之前插入):
41
+
42
+ ```typescript
43
+ // 检查 agent 是否异常退出(非超时非零退出码)
44
+ if (result.exitCode !== 0 && !isTimeoutResult(result)) {
45
+ if (mode === "full-auto") {
46
+ throw new Error(`Agent ${step.loopAgentName} 异常退出 (exit ${result.exitCode}): ${result.stderr.slice(0, 200)}`);
47
+ } else {
48
+ const choice = await uiSelect(ctx, `❌ ${step.loopAgentName} 异常退出 (exit ${result.exitCode})`, [
49
+ "1. 重新执行", "2. 跳过此步骤", "3. 取消工作流",
50
+ ]);
51
+ if (!choice || choice.startsWith("3")) { cancelWorkflow(); return; }
52
+ if (choice.startsWith("2")) { state.status = "skipped"; return; }
53
+ // 重新执行
54
+ result = await runAgentWithProgress(loopAgent, `[RETRY]\n\n${loopTask}`, stepIndex, step.loopAgentName!, step.timeoutMs);
55
+ }
56
+ }
57
+ ```
58
+
59
+ - **验证方式**:运行 `node tests/test-workflow-engine-bugs.mjs` 确认测试通过
60
+
61
+ ### 步骤 2:修复 setTimeout cleanupWidget 竞态条件(Bug B)
62
+
63
+ - **前置条件**:步骤 1 完成
64
+ - **改动文件**:`extensions/workflow-engine.ts`
65
+ - **改动位置**:
66
+ 1. 第 1436 行:`executeWorkflowBackground` 函数末尾的 `setTimeout(() => cleanupWidget(), 5000);`
67
+ 2. 第 1648 行:`cancelWorkflow` 回调中的 `setTimeout(() => cleanupWidget(), 5000);`
68
+ - **改动内容**:引入一个模块级别的定时器 ID 变量 `_cleanupTimer: ReturnType<typeof setTimeout> | null`,并在以下两个位置修改:
69
+
70
+ 1. 声明新变量(在全局变量区域,约第 606 行附近):
71
+ ```typescript
72
+ let _cleanupTimer: ReturnType<typeof setTimeout> | null = null;
73
+ ```
74
+
75
+ 2. 修改第 1436 行的 `setTimeout`:
76
+ ```typescript
77
+ // 清除之前的定时器
78
+ if (_cleanupTimer) clearTimeout(_cleanupTimer);
79
+ _cleanupTimer = setTimeout(() => {
80
+ _cleanupTimer = null;
81
+ cleanupWidget();
82
+ }, 5000);
83
+ ```
84
+
85
+ 3. 修改第 1648 行的 `setTimeout`:
86
+ ```typescript
87
+ if (_cleanupTimer) clearTimeout(_cleanupTimer);
88
+ _cleanupTimer = setTimeout(() => {
89
+ _cleanupTimer = null;
90
+ cleanupWidget();
91
+ }, 5000);
92
+ ```
93
+
94
+ 4. 在 `initWidget` 函数中(约第 639 行)添加清除逻辑,确保新工作流启动时取消旧定时器:
95
+ ```typescript
96
+ if (_cleanupTimer) {
97
+ clearTimeout(_cleanupTimer);
98
+ _cleanupTimer = null;
99
+ }
100
+ ```
101
+
102
+ 5. 在 `cleanupWidget` 函数中(约第 790 行)添加清除逻辑:
103
+ ```typescript
104
+ if (_cleanupTimer) {
105
+ clearTimeout(_cleanupTimer);
106
+ _cleanupTimer = null;
107
+ }
108
+ ```
109
+
110
+ - **验证方式**:运行 `node tests/test-workflow-engine-bugs.mjs` 确认测试通过
111
+
112
+ ### 步骤 3:编写测试用例
113
+
114
+ - **前置条件**:步骤 1 和步骤 2 完成
115
+ - **新增文件**:`tests/test-workflow-engine-bugs.mjs`
116
+ - **测试内容**:
117
+
118
+ **Bug A 测试**:
119
+ - **测试 1**:模拟 `SubagentResult` 对象,验证 `executeLoopGroup` 在收到 `exitCode: 1` 且 `stderr: "some error"` 时的行为
120
+ - 构造 `{ exitCode: 1, stderr: "Agent crashed: OOM", output: "" }`
121
+ - 验证 `isTimeoutResult` 返回 `false`
122
+ - 验证自定义的 simulate 函数能正确识别非零退出码
123
+ - **测试 2**:验证 `executeSingleStep` 已有 exitCode 检查(确认现有行为不被破坏)
124
+ - **测试 3**:验证 `isTimeoutResult` 对 `{ exitCode: -1, stderr: "timed out" }` 返回 `true`(确认超时仍被正确识别)
125
+
126
+ **Bug B 测试**:
127
+ - **测试 4**:模拟定时器竞态场景
128
+ - 验证 `initWidget` 被调用时能清除旧的 `_cleanupTimer`
129
+ - 验证 `cleanupWidget` 被调用时能清除 `_cleanupTimer`
130
+ - 验证新工作流启动后,旧定时器不会触发
131
+
132
+ - **验证方式**:运行 `node tests/test-workflow-engine-bugs.mjs`
133
+
134
+ ## 依赖关系
135
+
136
+ - 步骤 1 和步骤 2 相互独立,可并行实施
137
+ - 步骤 3 依赖步骤 1 和步骤 2 完成
138
+
139
+ ## 测试策略
140
+
141
+ - **Bug A 单元测试**:通过模拟 `SubagentResult` 对象和 `isTimeoutResult` 函数,验证非零退出码被正确识别和处理
142
+ - **Bug B 单元测试**:通过模拟定时器 ID 管理和 `initWidget` 的清理行为,验证竞态条件被消除
143
+ - **回归测试**:运行现有测试 `node tests/test-workflow-engine.mjs` 确认无破坏
144
+
145
+ ## 注意事项
146
+
147
+ 1. **最小化改动**:只插入必要的新逻辑,不重构现有代码结构
148
+ 2. **与 executeSingleStep 保持一致**:Bug A 的修复逻辑应与 `executeSingleStep` 第 1146 行的 exitCode 检查保持一致
149
+ 3. **定时器清除顺序**:在 `initWidget` 中清除旧定时器必须在设置 `_workflowRunning = true` **之前**完成,确保不会在旧定时器触发和新定时器设置之间出现窗口期
150
+ 4. **手动确认**:部署后需手动测试快速连续启动两个工作流的场景
@@ -0,0 +1,108 @@
1
+ {
2
+ "version": 2,
3
+ "createdAt": "2026-05-20T08:26:22.641Z",
4
+ "updatedAt": "2026-05-20T08:26:22.641Z",
5
+ "prompt": "[fix] 修复 extensions/workflow-engine.ts 1179行的let agentResult = await runAgentWithProgress(loopAgent, loopTask, stepIndex, step.loopAgentName!, step.timeoutMs);和1432行-1435行的 sendWorkflowResult(pi, finalState, prompt, _workflowType); // Cleanup widget after delay setTimeout(() => cleanupWidget(), 5000); 中的 1179行:executeLoopGroup 函数在调用 runAgentWithProgress 后没有检查 agentResult.exitCode。如果 sub-agent 进程非正常退出(例如崩溃或报错),工作流会忽略该错误并继续尝试运行 Reviewer。建议检查退出码,并在失败时抛出异常或中断循环。1432行:使用 setTimeout 延迟 5 秒执行 cleanupWidget 存在竞态风险。如果用户在工作流完成后 5 秒内立即启动了一个新的工作流,这个定时器触发时会调用 cleanupWidget 并将全局变量 _workflowRunning 重置为 false,从而干扰甚至中断正在运行的新工作流。建议通过对比工作流启动时间戳或在启动新工作流时显式取消之前的定时器来解决。\n\n**背景**:\n- 输入:见代码上下文\n- 预期行为:修复问题,但不能破坏原因功能结构和其他代码\n- 当前错误:请描述当前错误\n**任务**:\n1. 不要仅仅消除报错(Suppress),要解决根本原因。\n2. 先读取相关代码和日志,诊断根因(多步推理,不要先给结论)。\n3. 提供至少一种修复方案,并说明为什么这样做。\n4. 编写测试用例复现该 Bug 并确认修复有效。\n**输出**:提供 diff 和两句话的根因分析。\n**约束**:只修 bug,不做重构;最小化改动;不要假设错误是微不足道的。\n**验证**:运行 tests通过 确认修复。",
6
+ "mode": "attended",
7
+ "steps": [
8
+ {
9
+ "status": "done",
10
+ "durationMs": 279725
11
+ },
12
+ {
13
+ "status": "done",
14
+ "loopCount": 1,
15
+ "durationMs": 828233
16
+ }
17
+ ],
18
+ "currentStepIndex": 1,
19
+ "loopCounts": {
20
+ "worker-reviewer": 1
21
+ },
22
+ "planFilePath": ".pi-dev-output/pi-plans/20260520-153000-fix-workflow-engine-bugs.md",
23
+ "taskSummary": "fix - 修复 extensions/workflow-engine.ts 1179行的let agentResult = await runAgentWithProgress(loopAgent, loopTask, stepIndex, step.loopAgentName!, step.timeoutMs);和1432行-1435行的 sendWorkflowResult(pi, finalState, prompt, _workflowType); // Cleanup widget after delay setTimeout(() => cleanupWidget(), 5000); 中的 1179行:executeLoopGroup 函数在调用 runAgentWithProgress 后没有检查 agentResult.exitCode。如果 sub-agent 进程非正常退出(例如崩溃或报错),工作流会忽略该错误并继续尝试运行 Reviewer。建议检查退出码,并在失败时抛出异常或中断循环。1432行:使用 setTimeout 延迟 5 秒执行 cleanupWidget 存在竞态风险。如果用户在工作流完成后 5 秒内立即启动了一个新的工作流,这个定时器触发时会调用 cleanupWidget 并将全局变量 _workflowRunning 重置为 false,从而干扰甚至中断正在运行的新工作流。建议通过对比工作流启动时间戳或在启动新工作流时显式取消之前的定时器来解决。",
24
+ "workflowType": "自定义",
25
+ "fileChanges": [
26
+ {
27
+ "agent": "planner",
28
+ "stepIndex": 0,
29
+ "type": "edit",
30
+ "filePath": ".gitignore",
31
+ "timestamp": "2026-05-20T08:11:38.329Z"
32
+ },
33
+ {
34
+ "agent": "planner",
35
+ "stepIndex": 0,
36
+ "type": "new",
37
+ "filePath": ".pi-dev-output/",
38
+ "timestamp": "2026-05-20T08:11:38.342Z"
39
+ },
40
+ {
41
+ "agent": "worker",
42
+ "stepIndex": 1,
43
+ "type": "edit",
44
+ "filePath": "extensions/workflow-engine.ts",
45
+ "timestamp": "2026-05-20T08:24:02.896Z"
46
+ },
47
+ {
48
+ "agent": "worker",
49
+ "stepIndex": 1,
50
+ "type": "edit",
51
+ "filePath": "tests/test-workflow-engine-bugs.mjs",
52
+ "timestamp": "2026-05-20T08:24:02.897Z"
53
+ },
54
+ {
55
+ "agent": "reviewer",
56
+ "stepIndex": 1,
57
+ "type": "edit",
58
+ "filePath": "extensions/workflow-engine.ts",
59
+ "timestamp": "2026-05-20T08:26:22.616Z"
60
+ },
61
+ {
62
+ "agent": "reviewer",
63
+ "stepIndex": 1,
64
+ "type": "edit",
65
+ "filePath": "tests/test-workflow-engine-bugs.mjs",
66
+ "timestamp": "2026-05-20T08:26:22.616Z"
67
+ }
68
+ ],
69
+ "subAgentRuns": 3,
70
+ "filesModified": 5,
71
+ "filesCreated": 1,
72
+ "agentRunHistory": [
73
+ {
74
+ "agent": "planner",
75
+ "stepIndex": 0,
76
+ "startedAt": "2026-05-20T08:06:58.619Z",
77
+ "durationMs": 279685,
78
+ "exitCode": 0,
79
+ "toolCount": 0
80
+ },
81
+ {
82
+ "agent": "worker",
83
+ "stepIndex": 1,
84
+ "startedAt": "2026-05-20T08:12:34.409Z",
85
+ "durationMs": 688481,
86
+ "exitCode": 0,
87
+ "toolCount": 2
88
+ },
89
+ {
90
+ "agent": "reviewer",
91
+ "stepIndex": 1,
92
+ "startedAt": "2026-05-20T08:24:02.928Z",
93
+ "durationMs": 139684,
94
+ "exitCode": 0,
95
+ "toolCount": 4
96
+ }
97
+ ],
98
+ "baseline": [
99
+ {
100
+ "path": "extensions/workflow-engine.ts",
101
+ "hash": "7f0ec6eb9a91d57dd31335c360a910da53c3b1ea"
102
+ },
103
+ {
104
+ "path": "package.json",
105
+ "hash": "fa8ac6dec6894988cbe6393b8c71f9d20c5188cd"
106
+ }
107
+ ]
108
+ }
package/README.md CHANGED
@@ -1,6 +1,6 @@
1
1
  # @ghyper9023/pi-dev-workflow
2
2
 
3
- > Developer workflow toolkit for [pi coding agent](https://pi.dev/): git agents, code review, Karpathy guidelines, themes
3
+ > Developer workflow toolkit for [pi coding agent](https://pi.dev/): git agents, code review, Karpathy guidelines, themes, automation workflows
4
4
 
5
5
  ## 快速安装
6
6
 
@@ -23,7 +23,21 @@ pi-package/
23
23
  ├── .gitignore
24
24
  ├── agents/
25
25
  │ ├── git-agent.md # git-sub-agent 定义(专注 git 操作)
26
- └── review-agent.md # review-sub-agent 定义(专注代码审查)
26
+ ├── review-agent.md # review-sub-agent 定义(专注代码审查)
27
+ │ ├── grill/ # 设计评审 (Grill) agent 定义
28
+ │ │ ├── dev-grill-agent.md # 通用 /dev-feat Grill agent
29
+ │ │ ├── dev-fix-grill-agent.md # /dev-fix 根因分析评审
30
+ │ │ ├── dev-doc-grill-agent.md # /dev-doc 文档大纲评审
31
+ │ │ ├── dev-refactor-grill-agent.md
32
+ │ │ ├── dev-test-grill-agent.md
33
+ │ │ ├── dev-perf-grill-agent.md
34
+ │ │ └── dev-prd-agent.md # PRD 生成 agent
35
+ │ └── workflow/ # 自动化工作流 agent 定义
36
+ │ ├── planner-agent.md # 计划制定 agent
37
+ │ ├── worker-agent.md # 代码实施 agent
38
+ │ ├── reviewer-agent.md # 代码审查 agent
39
+ │ ├── trimmer-agent.md # 代码精简 agent
40
+ │ └── docWriter-agent.md # 文档撰写 agent
27
41
  ├── prompts/
28
42
  │ ├── APPEND_SYSTEM.md # 全局追加提示:强制使用简体中文+英文专业名词
29
43
  │ ├── review-commit.md # 审查 commit 的提示模板
@@ -41,7 +55,8 @@ pi-package/
41
55
  │ ├── dev-prompts.ts # 提示词优化向导(/dev-* 命令)
42
56
  │ ├── git-commands.ts # git-sub-agent 命令
43
57
  │ ├── grill-me-agent.ts # Grill + PRD 运行时:设计评审、PRD 生成
44
- └── sub-agents.ts # 子代理系统:git-sub-agent + review-sub-agent
58
+ ├── sub-agents.ts # 子代理系统:git-sub-agent + review-sub-agent
59
+ │ └── workflow-engine.ts # 工作流编排引擎(由 dev-prompts.ts 引入)
45
60
  └── themes/
46
61
  └── claude-code-theme.json # Claude Code CLI 风格主题
47
62
  ```
@@ -76,7 +91,7 @@ pi-package/
76
91
  | **3** / Esc | 不是审查(放行给主代理) | 不启动子代理,原消息交给主 AI 处理 |
77
92
 
78
93
  也支持 `/skill:review-html` 直接触发阻塞审查。
79
- 审查结果以交互式 HTML 报告形式写入 `pi-review/` 目录。
94
+ 审查结果以交互式 HTML 报告形式写入 `.pi-dev-output/pi-review/html/` 目录。
80
95
 
81
96
  ### subagent 工具
82
97
 
@@ -98,19 +113,19 @@ LLM 也可以直接调用 `subagent` 工具委派任务给任意子代理:
98
113
 
99
114
  ### 命令一览
100
115
 
101
- | 命令 | 用途 | 对应模板类型 |
102
- |---|---|---|
103
- | `/dev-feat` | 新功能/创意生成 | `feat` |
104
- | `/dev-fix` | 问题排查/错误修正 | `fix` |
105
- | `/dev-doc` | 文档生成/总结 | `doc` |
106
- | `/dev-refactor` | 重构/优化现有结构 | `refactor` |
107
- | `/dev-test` | 测试用例生成 | `test` |
108
- | `/dev-chore` | 日常维护/自动化 | `chore` |
109
- | `/dev-perf` | 性能优化 | `perf` |
110
- | `/dev-style` | 风格/格式调整 | `style` |
111
- | `/dev-security` | 安全审查 | `security` |
112
- | `/dev-explain` | 概念解释 | `explain` |
113
- | `/dev-compare` | 对比评估 | `compare` |
116
+ | 命令 | 用途 | 对应模板类型 | 含工作流 |
117
+ |------|------|-------------|---------|
118
+ | `/dev-feat` | 新功能/创意生成 | `feat` | ✅ |
119
+ | `/dev-fix` | 问题排查/错误修正 | `fix` | ✅ |
120
+ | `/dev-doc` | 文档生成/总结 | `doc` | ✅ |
121
+ | `/dev-refactor` | 重构/优化现有结构 | `refactor` | ✅ |
122
+ | `/dev-test` | 测试用例生成 | `test` | ✅ |
123
+ | `/dev-perf` | 性能优化 | `perf` | ✅ |
124
+ | `/dev-style` | 风格/格式调整 | `style` | ✅ |
125
+ | `/dev-security` | 安全审查 | `security` | ✅ |
126
+ | `/dev-chore` | 日常维护/自动化 | `chore` | ❌(传统模式) |
127
+ | `/dev-explain` | 概念解释 | `explain` | ❌(传统模式) |
128
+ | `/dev-compare` | 对比评估 | `compare` | ❌(传统模式) |
114
129
 
115
130
  ### 使用方法
116
131
 
@@ -161,7 +176,7 @@ Bug 描述? 创建用户成功后返回 201,但实际上返回了 500
161
176
 
162
177
  组装后的提示词包含:角色(技术文档工程师)→ 大纲先行 → Markdown 层级文档 → 2 个可运行示例。
163
178
 
164
- ### 示例 3:用 `/dev-feat` 走完整流程(含 Grill + PRD)
179
+ ### 示例 3:用 `/dev-feat` 走完整流程(含 Grill + 自动化工作流 + PRD)
165
180
 
166
181
  ```text
167
182
  /dev-feat
@@ -172,19 +187,125 @@ Bug 描述? 创建用户成功后返回 201,但实际上返回了 500
172
187
 
173
188
  → 填写完成后,弹出确认框:
174
189
  🔍 设计方案评审 — 是否进入设计评审 (Grill) 模式?
175
- 选择"是"后,AI 生成约 15-25 道问题,逐题展示:
190
+ 逐题回答完毕(约 15-25 题),评审记录附加到提示词末尾。
191
+
192
+ → 弹出工作流确认框:
193
+ 🚀 进入自动化工作流?
194
+ 工作流将自动执行以下步骤:
195
+ 1. 📋 Planner — 分析代码库并生成实施计划
196
+ 2. 🔧 Worker → Reviewer — 实施代码并审查
197
+ 3. ✂️ Trimmer → Reviewer — 精简代码并审查
198
+ 4. 📝 DocWriter — 更新文档
199
+
200
+ → 选择"是"后,工作流开始执行...
176
201
 
177
- 问题 1/18:支付数据流 — 支付请求的完整数据流是怎样的?
178
- (a) 客户端 API → 支付网关 → 回调 → 数据库
179
- (b) 客户端 API 消息队列 → 支付网关 → 回调 → Webhook → 数据库
180
- (c) 客户端直连支付网关 前端回调 API → 数据库
202
+ 📋 工作流进度
203
+ 📋 生成实施计划
204
+ 🔧 实施代码审查
205
+ ✂️ 精简代码审查
206
+ ⬜ 📝 更新文档
181
207
 
182
- 逐题回答完毕后,提示词增强并投递给主代理执行。
183
- 执行完成后,弹出 PRD 确认框:
208
+ Planner 完成 ✅,计划写入 .pi-dev-output/pi-plans/
209
+ Worker + Reviewer 循环开始... 审查发现 critical 问题,自动进入第 2 轮循环...
210
+ → 所有步骤完成后:🎉 工作流全部完成!
211
+
212
+ → 弹出 PRD 确认框:
184
213
  📋 创建 PRD — 是否为此功能创建 PRD 文档?
185
- → 选择"是",PRD 保存到 pi-dev-output/pi-prd/payments-20260517.md
186
- → 选择"🚀 根据 PRD 开始开发"进行后续迭代。
214
+ → 选择"是",PRD 保存到 .pi-dev-output/pi-prd/payments-20260519.md
215
+ ```
216
+
217
+ ---
218
+
219
+ ## Automation Workflow(自动化工作流引擎)
220
+
221
+ > 自 v0.4.0 起支持
222
+
223
+ `/dev-*` 向导组装完提示词后,除了直接发送给主代理(传统模式),还可以选择进入 **自动化工作流** — 由一组专业的 sub-agent 按预设步骤链自动执行,无需人工逐条指令干预。
224
+
225
+ 工作流由 `extensions/workflow-engine.ts` 编排,在 `extensions/dev-prompts.ts` 中定义各命令的步骤链。每个步骤启动一个独立的 sub-agent 进程,拥有隔离的上下文窗口。
226
+
227
+ ### Workflow Agent 一览
228
+
229
+ 5 个专用 sub-agent 各司其职,定义在 `agents/workflow/` 目录下:
230
+
231
+ | Agent | 职责 | 定义文件 |
232
+ |-------|------|---------|
233
+ | **planner** | 分析代码库,生成详细的实施计划并写入 `.pi-dev-output/pi-plans/` | `agents/workflow/planner-agent.md` |
234
+ | **worker** | 按计划逐步实现代码改动(严格遵循计划,不做计划外修改) | `agents/workflow/worker-agent.md` |
235
+ | **reviewer** | 审查代码质量,输出带严重等级的结构化报告(critical/medium/low) | `agents/workflow/reviewer-agent.md` |
236
+ | **trimmer** | 精简冗余代码、缩短冗长行、消除重复逻辑,优化可读性 | `agents/workflow/trimmer-agent.md` |
237
+ | **docWriter** | 根据代码最新状态更新 README 和代码注释 | `agents/workflow/docWriter-agent.md` |
238
+
239
+ ### 工作流模式
240
+
241
+ 步骤执行前,弹出模式选择对话框:
242
+
243
+ | 模式 | 说明 |
244
+ |------|------|
245
+ | **值守**(默认 / attended) | 自动步骤自动执行,`[confirm]` 步骤需用户确认,loop-group 循环需用户许可 |
246
+ | **完全信任**(full-auto) | 全自动运行,无任何确认步骤。超时自动重试一次,循环自动进入下一轮 |
247
+ | **完全值守**(full-attended) | 每一步(包括 auto 类型步骤)都需用户确认后才执行 |
248
+
249
+ ### 命令工作流一览
250
+
251
+ 每个 `/dev-*` 命令对应不同的步骤链。以下配置定义在 `extensions/dev-prompts.ts` 的 `WORKFLOW_STEPS` 常量中:
252
+
253
+ 图例:
254
+ - `{}` — Loop-Group(执行 → 审查 → 循环,直到无严重问题或达最大次数)
255
+ - `[]` — Confirm 步骤(需用户确认是否执行)
256
+ - `→` — 顺序执行
257
+
258
+ | 命令 | 工作流步骤 | 说明 |
259
+ |------|-----------|------|
260
+ | `/dev-feat` | planner → {worker→reviewer} → {trimmer→reviewer} → [docWriter] | 完整流程:计划 → 实施+审查 → 精简+审查 → 文档(可跳过) |
261
+ | `/dev-fix` | planner → {worker→reviewer} → [docWriter] | 无 trimmer 阶段 |
262
+ | `/dev-refactor` | planner → {worker→reviewer} → {trimmer→reviewer} | 无 docWriter 阶段 |
263
+ | `/dev-perf` | planner → {worker→reviewer} | 无 trimmer 和 docWriter |
264
+ | `/dev-test` | planner → {worker→reviewer} | 同上 |
265
+ | `/dev-doc` | planner → docWriter | 简化流程,直接计划→撰写 |
266
+ | `/dev-style` | {trimmer→reviewer} | 无计划阶段,仅精简+审查(最多 2 轮循环) |
267
+ | `/dev-security` | reviewer | 仅安全审查 |
268
+ | `/dev-chore` | 无工作流 | 传统模式,直接发送 prompt |
269
+ | `/dev-explain` | 无工作流 | 传统模式 |
270
+ | `/dev-compare` | 无工作流 | 传统模式 |
271
+
272
+ ### 断点续传 (Checkpoint)
273
+
274
+ 工作流在执行过程中会定期保存 checkpoint 到 `.pi-dev-output/pi-workflow/checkpoint.json`。如果工作流因终端关闭、网络断开或 AI 超时而中断,后续恢复方式如下:
275
+
276
+ - **自动恢复**:再次执行对应的 `/dev-*` 命令时,引擎自动检测 checkpoint 文件,弹出确认对话框询问是否恢复
277
+ - **手动恢复**:注册了专门的 `/dev-workflow-continue` 命令,用于手动恢复上次中断的工作流
278
+ - **Checkpoint 内容**:包含原始 prompt、运行模式、各步骤状态、loop 次数、plan 文件引用路径
279
+
280
+ 如果在恢复对话框中选择"否",则丢弃 checkpoint 重新开始。
281
+
282
+ ### Loop-Group 循环审查
283
+
284
+ `{}` 标记的步骤组称为 Loop-Group。机制如下:
285
+
286
+ 1. 先执行实施 agent(worker 或 trimmer),再执行 reviewer agent
287
+ 2. Reviewer 输出 `[REVIEW_SUMMARY]` JSON 摘要:
288
+
187
289
  ```
290
+ [REVIEW_SUMMARY]
291
+ {"maxSeverity":"critical","critical":2,"medium":1,"low":3}
292
+ [/REVIEW_SUMMARY]
293
+ ```
294
+
295
+ 3. 若 `maxSeverity === "critical"` 且未达到最大循环次数(默认 3 次),进入下一轮循环
296
+ 4. 在 `full-auto` 模式下自动循环;在 `attended` 模式下询问用户是否继续
297
+ 5. 达到最大循环次数后,无论审查结果如何,进入下一步
298
+ 6. Reviewer 输出支持 fallback 裸 JSON 解析(兜底识别)
299
+
300
+ ### 超时处理
301
+
302
+ 每个步骤有独立的超时时间(`timeoutMs` 字段)。超时后的行为因模式而异:
303
+
304
+ | 模式 | 超时行为 |
305
+ |------|---------|
306
+ | `full-auto` | 自动重试一次(带 `[RETRY]` 前缀),重试仍超时则步骤标记为 failed |
307
+ | `attended` / `full-attended` | 弹出选择:重新执行 / 跳过此步骤 / 取消工作流 |
308
+ | loop-group 内 | 超时后不阻塞循环,可自动进入审查阶段(带 `[TIMEOUT_WARNING]` 标记) |
188
309
 
189
310
  ## Skills
190
311
 
@@ -193,7 +314,7 @@ Bug 描述? 创建用户成功后返回 201,但实际上返回了 500
193
314
  | **karpathy-guidelines** | [forrestchang/andrej-karpathy-skills](https://github.com/forrestchang/andrej-karpathy-skills) | 基于 Andrej Karpathy 对 LLM 编码陷阱的观察,强调简洁、精准、可验证 |
194
315
  | **review-html** | 自制 | git diff / commit 审查,输出自包含的交互式 HTML 报告 |
195
316
  | **grill-with-docs** | [mattpocock/skills](https://github.com/mattpocock/skills) | 设计评审 — 挑战方案、统一术语、实时更新 CONTEXT.md 和 ADR |
196
- | **to-prd** | [mattpocock/skills](https://github.com/mattpocock/skills) | 从对话上下文和代码库理解生成 PRD,保存到 `pi-dev-output/pi-prd/` |
317
+ | **to-prd** | [mattpocock/skills](https://github.com/mattpocock/skills) | 从对话上下文和代码库理解生成 PRD,保存到 `.pi-dev-output/pi-prd/` |
197
318
 
198
319
  ## 设计评审(Grill)机制
199
320
 
@@ -234,7 +355,7 @@ Grill("拷问式评审")是提交方案前由 AI sub-agent 从多个维度
234
355
  1. **等待** — 等待主代理完成任务(`ctx.waitForIdle()`)
235
356
  2. **确认** — 弹出对话框询问是否创建 PRD
236
357
  3. **生成** — sub-agent 读取对话上下文 + 代码库理解,按模板生成 Markdown PRD
237
- 4. **保存** — 写入 `pi-dev-output/pi-prd/<module>-<date>.md`,自动创建 `.gitignore` 忽略该目录
358
+ 4. **保存** — 写入 `.pi-dev-output/pi-prd/<module>-<date>.md`
238
359
  5. **后续操作** — 询问是否立即开始开发:
239
360
  - "是" — 将 PRD 作为开发指令发送给主代理
240
361
  - "否" — 仅保存文件,稍后手动引用
@@ -289,6 +410,27 @@ A: 评审问答以「设计评审记录」区块追加到原提示词末尾,
289
410
  **Q: `grill-with-docs` skill 和 `/dev-*` 内置的 Grill 有什么区别?**
290
411
  A: `grill-with-docs` 是可独立调用的 skill(`/skill:grill-with-docs`),侧重领域术语统一和文档同步(更新 CONTEXT.md、创建 ADR)。`/dev-*` 内置的 Grill 是任务向导的一部分,侧重方案评审,不涉及文档持久化。
291
412
 
413
+ **Q: 工作流执行到一半中断了怎么办?**
414
+ A: 工作流引擎会在每次步骤完成后保存 checkpoint 到 `.pi-dev-output/pi-workflow/checkpoint.json`。重新执行对应的 `/dev-*` 命令时会自动检测并询问是否恢复。也可手动使用 `/dev-workflow-continue` 命令恢复上次中断的工作流。
415
+
416
+ **Q: 如何跳过工作流,直接发送 prompt 给主代理?**
417
+ A: 在工作流确认对话框中选择"否"即可直接发送 prompt 给主代理,行为与传统模式完全一致。
418
+
419
+ **Q: `{}` loop-group 最多循环多少次?会无限循环吗?**
420
+ A: 不会无限循环。每个 loop-group 默认最大循环次数为 3(由 `maxLoops` 字段控制),达到上限后无论审查结果如何都会进入下一步。`/dev-style` 的 loop-group 最大次数为 2。如果使用 `full-auto` 模式且问题重复出现,达到上限后自动结束循环。
421
+
422
+ **Q: reviewer 的审查等级如何决定 workflow 走向?**
423
+ A: reviewer 输出 `[REVIEW_SUMMARY]` JSON 块,`maxSeverity: "critical"` 时触发下一轮循环(如果未达上限),`"medium"` 或 `"low"` 时结束循环进入下一步。
424
+
425
+ **Q: docWriter 步骤为什么要标记为 `[confirm]`?**
426
+ A: 文档更新是可选的。有时代码变更只是内部重构或 Bug 修复,不需要更新 README。`[confirm]` 允许用户跳过此步骤。
427
+
428
+ **Q: 超时后会发生什么?**
429
+ A: 在 `full-auto` 模式下超时会自动重试一次;在 `attended` 模式下会弹出对话框让用户选择:重新执行、跳过此步骤、取消工作流。重试后仍然超时则该步骤标记为 failed。
430
+
431
+ **Q: 所有命令都支持自动化工作流吗?**
432
+ A: 不是。`/dev-chore`、`/dev-explain`、`/dev-compare` 三个命令无工作流配置,使用传统模式直接发送 prompt。其余 8 个命令均包含工作流支持。具体各命令的步骤链见「命令工作流一览」表格。
433
+
292
434
  ## License
293
435
 
294
436
  MIT
@@ -1,6 +1,6 @@
1
1
  ---
2
2
  name: review-agent
3
- description: Review 代码,生成 HTML 审查报告并输出到 pi-review/ 目录
3
+ description: Review 代码,生成 HTML 审查报告并输出到 .pi-dev-output/pi-review/html/ 目录
4
4
  tools: read, write, bash, grep, find, ls
5
5
  ---
6
6
 
@@ -14,9 +14,9 @@ tools: read, write, bash, grep, find, ls
14
14
  2. **获取改动**:运行 `git diff`(未提交改动)或 `git log -p -n 3`(最近提交),查看代码变更。
15
15
  3. **分析审查**:按 skill 中的约束检查 BUG、敏感信息、可维护性、规范等。
16
16
  4. **生成 HTML**:按 skill 的 HTML 约束生成完整的自包含 HTML 审查报告。
17
- 5. **写入文件**:使用 `write` 工具将 HTML 保存到 `pi-dev-output/pi-review/` 目录。
17
+ 5. **写入文件**:使用 `write` 工具将 HTML 保存到 `.pi-dev-output/pi-review/html/` 目录。
18
18
  - 文件名格式:`YYYYMMDD-HHmm-任务简述-index.html`
19
- - `pi-review/` 目录不存在则先 mkdir 创建(已存在于 .gitignore)
19
+ - `.pi-dev-output/pi-review/html/` 目录不存在则先 mkdir 创建
20
20
  6. **汇报结果**:stdout 只输出以下格式的简要总结,**不要输出 HTML 内容到 stdout**:
21
21
 
22
22
  ```
@@ -24,14 +24,14 @@ tools: read, write, bash, grep, find, ls
24
24
  <summary>审查完成,报告文件</summary>
25
25
  <details>
26
26
  - 审查范围: git diff (X files changed)
27
- - 报告: pi-dev-output/pi-review/20260513-xxxx-xxx-index.html
27
+ - 报告: .pi-dev-output/pi-review/html/20260513-xxxx-xxx-index.html
28
28
  - 发现问题: X bugs, X warnings, X suggestions
29
29
  </details>
30
30
  ```
31
31
 
32
32
  ## 重要规则
33
33
 
34
- - HTML 必须**写文件到 pi-dev-output/pi-review/**,**不要输出到 stdout**
34
+ - HTML 必须**写文件到 .pi-dev-output/pi-review/html/**,**不要输出到 stdout**
35
35
  - stdout 只输出上面的简短结构化摘要(参考 git-agent 的做法)
36
36
  - 使用 `bash` 运行 git 命令和创建目录
37
37
  - 使用 `write` 工具写 HTML 文件
@@ -0,0 +1,29 @@
1
+ ---
2
+ name: docWriter
3
+ description: 文档撰写 agent — 更新 README 及 API 文档,添加代码注释
4
+ tools: read, bash, write, find, ls, grep
5
+ ---
6
+
7
+ 你是一个技术文档工程师。你的任务是根据代码库的最新状态以及从最近几次git-commit或git-diff中的改动,更新 README 和必要的代码注释。
8
+
9
+ ## 工作流程
10
+
11
+ 1. **探索代码**:使用 `read` / `find` / `ls` / `bash` 了解当前项目结构和最新改动。
12
+ 2. **读取已有文档**:先 `read` 现有的 README.md 和其他关键文档。
13
+ 3. **识别文档缺口**:
14
+ - 新增的功能或模块是否已在 README 中记录?
15
+ - 变更的 API 是否需要更新文档?
16
+ - 关键函数/类是否缺少注释?
17
+ 4. **更新文档**:
18
+ - 更新 README.md:添加新功能说明、更新 API 文档、修改过时信息
19
+ - 添加/更新代码注释:对关键函数添加 JSDoc/TSDoc 注释
20
+ - 保持文档风格与现有文档一致
21
+
22
+ ## 约束
23
+
24
+ - **不要修改业务逻辑代码**(只添加或修改注释/文档)
25
+ - 注释应说明"为什么"而非"是什么"
26
+ - 使用项目已有的注释风格
27
+ - 如果项目没有 README,创建一个基本的 README.md
28
+ - 避免文档膨胀:只记录必要的、稳定的接口和功能
29
+ - 确保文档与实际代码行为一致