@fitlab-ai/agent-infra 0.8.3 → 0.8.4

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 (100) hide show
  1. package/README.zh-CN.md +10 -0
  2. package/bin/cli.ts +1 -1
  3. package/dist/bin/cli.js +1 -1
  4. package/dist/lib/cp.js +56 -15
  5. package/dist/lib/defaults.json +1 -0
  6. package/dist/lib/sandbox/capture.js +5 -3
  7. package/dist/lib/sandbox/clipboard/bridge.js +12 -9
  8. package/dist/lib/sandbox/clipboard/inbox.js +82 -0
  9. package/dist/lib/sandbox/commands/create.js +39 -23
  10. package/dist/lib/sandbox/runtimes/base.dockerfile +3 -0
  11. package/dist/lib/sandbox/shell.js +9 -1
  12. package/dist/lib/sandbox/tools.js +2 -2
  13. package/lib/cp.ts +56 -15
  14. package/lib/defaults.json +1 -0
  15. package/lib/sandbox/capture.ts +5 -3
  16. package/lib/sandbox/clipboard/bridge.ts +14 -12
  17. package/lib/sandbox/clipboard/inbox.ts +83 -0
  18. package/lib/sandbox/commands/create.ts +48 -24
  19. package/lib/sandbox/runtimes/base.dockerfile +3 -0
  20. package/lib/sandbox/shell.ts +11 -2
  21. package/lib/sandbox/tools.ts +5 -5
  22. package/package.json +1 -1
  23. package/templates/.agents/README.en.md +3 -0
  24. package/templates/.agents/README.zh-CN.md +3 -0
  25. package/templates/.agents/rules/create-issue.github.en.md +1 -1
  26. package/templates/.agents/rules/create-issue.github.zh-CN.md +1 -1
  27. package/templates/.agents/rules/review-handshake.en.md +2 -2
  28. package/templates/.agents/rules/review-handshake.zh-CN.md +2 -2
  29. package/templates/.agents/rules/testing-discipline.en.md +3 -41
  30. package/templates/.agents/rules/testing-discipline.zh-CN.md +3 -41
  31. package/templates/.agents/scripts/validate-artifact.js +93 -0
  32. package/templates/.agents/skills/analyze-task/SKILL.en.md +1 -1
  33. package/templates/.agents/skills/analyze-task/SKILL.zh-CN.md +2 -2
  34. package/templates/.agents/skills/archive-tasks/scripts/archive-tasks.sh +1 -1
  35. package/templates/.agents/skills/block-task/SKILL.en.md +1 -1
  36. package/templates/.agents/skills/block-task/SKILL.zh-CN.md +2 -2
  37. package/templates/.agents/skills/cancel-task/SKILL.en.md +1 -1
  38. package/templates/.agents/skills/cancel-task/SKILL.zh-CN.md +2 -2
  39. package/templates/.agents/skills/check-task/SKILL.zh-CN.md +9 -9
  40. package/templates/.agents/skills/close-codescan/SKILL.en.md +1 -1
  41. package/templates/.agents/skills/close-codescan/SKILL.zh-CN.md +2 -2
  42. package/templates/.agents/skills/close-dependabot/SKILL.en.md +1 -1
  43. package/templates/.agents/skills/close-dependabot/SKILL.zh-CN.md +2 -2
  44. package/templates/.agents/skills/code-task/SKILL.en.md +1 -1
  45. package/templates/.agents/skills/code-task/SKILL.zh-CN.md +1 -1
  46. package/templates/.agents/skills/code-task/reference/branch-management.zh-CN.md +2 -2
  47. package/templates/.agents/skills/code-task/reference/fix-mode.en.md +2 -2
  48. package/templates/.agents/skills/code-task/reference/fix-mode.zh-CN.md +2 -2
  49. package/templates/.agents/skills/code-task/reference/output-template.zh-CN.md +1 -1
  50. package/templates/.agents/skills/commit/SKILL.en.md +1 -1
  51. package/templates/.agents/skills/commit/SKILL.zh-CN.md +1 -1
  52. package/templates/.agents/skills/commit/reference/task-status-update.en.md +6 -6
  53. package/templates/.agents/skills/commit/reference/task-status-update.zh-CN.md +6 -6
  54. package/templates/.agents/skills/complete-manual-validation/SKILL.en.md +27 -3
  55. package/templates/.agents/skills/complete-manual-validation/SKILL.zh-CN.md +27 -3
  56. package/templates/.agents/skills/complete-task/SKILL.en.md +1 -1
  57. package/templates/.agents/skills/complete-task/SKILL.zh-CN.md +1 -1
  58. package/templates/.agents/skills/create-pr/SKILL.en.md +4 -4
  59. package/templates/.agents/skills/create-pr/SKILL.zh-CN.md +4 -4
  60. package/templates/.agents/skills/create-pr/reference/pr-body-template.en.md +1 -1
  61. package/templates/.agents/skills/create-pr/reference/pr-body-template.zh-CN.md +1 -1
  62. package/templates/.agents/skills/create-task/SKILL.en.md +2 -2
  63. package/templates/.agents/skills/create-task/SKILL.zh-CN.md +5 -5
  64. package/templates/.agents/skills/import-codescan/SKILL.en.md +2 -2
  65. package/templates/.agents/skills/import-codescan/SKILL.zh-CN.md +3 -3
  66. package/templates/.agents/skills/import-dependabot/SKILL.en.md +2 -2
  67. package/templates/.agents/skills/import-dependabot/SKILL.zh-CN.md +3 -3
  68. package/templates/.agents/skills/import-issue/SKILL.en.md +2 -2
  69. package/templates/.agents/skills/import-issue/SKILL.zh-CN.md +3 -3
  70. package/templates/.agents/skills/init-labels/SKILL.zh-CN.md +1 -1
  71. package/templates/.agents/skills/init-milestones/SKILL.en.md +3 -2
  72. package/templates/.agents/skills/init-milestones/SKILL.zh-CN.md +4 -3
  73. package/templates/.agents/skills/init-milestones/scripts/init-milestones.github.sh +165 -41
  74. package/templates/.agents/skills/plan-task/SKILL.en.md +1 -1
  75. package/templates/.agents/skills/plan-task/SKILL.zh-CN.md +2 -2
  76. package/templates/.agents/skills/restore-task/SKILL.en.md +1 -1
  77. package/templates/.agents/skills/restore-task/SKILL.zh-CN.md +1 -1
  78. package/templates/.agents/skills/review-analysis/SKILL.en.md +1 -1
  79. package/templates/.agents/skills/review-analysis/SKILL.zh-CN.md +1 -1
  80. package/templates/.agents/skills/review-analysis/reference/output-templates.en.md +5 -5
  81. package/templates/.agents/skills/review-analysis/reference/output-templates.zh-CN.md +5 -5
  82. package/templates/.agents/skills/review-code/SKILL.en.md +8 -4
  83. package/templates/.agents/skills/review-code/SKILL.zh-CN.md +6 -3
  84. package/templates/.agents/skills/review-code/config/verify.en.json +1 -0
  85. package/templates/.agents/skills/review-code/config/verify.zh-CN.json +1 -0
  86. package/templates/.agents/skills/review-code/reference/output-templates.en.md +5 -5
  87. package/templates/.agents/skills/review-code/reference/output-templates.zh-CN.md +5 -5
  88. package/templates/.agents/skills/review-code/reference/report-template.en.md +2 -2
  89. package/templates/.agents/skills/review-code/reference/report-template.zh-CN.md +2 -2
  90. package/templates/.agents/skills/review-plan/SKILL.en.md +1 -1
  91. package/templates/.agents/skills/review-plan/SKILL.zh-CN.md +1 -1
  92. package/templates/.agents/skills/review-plan/reference/output-templates.en.md +5 -5
  93. package/templates/.agents/skills/review-plan/reference/output-templates.zh-CN.md +5 -5
  94. package/templates/.agents/skills/test/SKILL.zh-CN.md +26 -8
  95. package/templates/.agents/skills/update-agent-infra/SKILL.zh-CN.md +1 -1
  96. package/templates/.agents/skills/update-agent-infra/scripts/sync-templates.js +29 -6
  97. package/templates/.agents/skills/watch-pr/SKILL.en.md +2 -2
  98. package/templates/.agents/skills/watch-pr/SKILL.zh-CN.md +2 -2
  99. package/templates/.agents/skills/watch-pr/reference/monitor-and-heal.en.md +8 -1
  100. package/templates/.agents/skills/watch-pr/reference/monitor-and-heal.zh-CN.md +8 -1
@@ -41,7 +41,7 @@ description: >
41
41
  当前项目未启用 PR 流程(`.agents/.airc.json` 中 `prFlow: "disabled"`)。
42
42
  无需创建 Pull Request,请直接运行:
43
43
  - Claude Code / OpenCode:/complete-task {task-ref}
44
- - Gemini CLI:/agent-infra:complete-task {task-ref}
44
+ - Gemini CLI:/{{project}}:complete-task {task-ref}
45
45
  - Codex CLI:$complete-task {task-ref}
46
46
  ```
47
47
 
@@ -105,7 +105,7 @@ description: >
105
105
  获取当前时间:
106
106
 
107
107
  ```bash
108
- date "+%Y-%m-%d %H:%M:%S%:z"
108
+ date "+%Y-%m-%d %H:%M:%S%z" | sed 's/\([+-][0-9][0-9]\)\([0-9][0-9]\)$/\1:\2/'
109
109
  ```
110
110
 
111
111
  如果获取到了 `{task-id}`,更新 task.md 的 `pr_number`、`pr_status`(设为 `created`)、`updated_at`、`agent_infra_version`,并追加 Create PR 的 Activity Log,记录元数据同步和摘要发布结果。
@@ -136,7 +136,7 @@ node .agents/scripts/validate-artifact.js gate create-pr .agents/workspace/activ
136
136
  ```
137
137
  下一步 - 监控 PR 检查(required checks 全绿前自动自愈):
138
138
  - Claude Code / OpenCode:/watch-pr {task-ref}
139
- - Gemini CLI:/agent-infra:watch-pr {task-ref}
139
+ - Gemini CLI:/{{project}}:watch-pr {task-ref}
140
140
  - Codex CLI:$watch-pr {task-ref}
141
141
  ```
142
142
 
@@ -145,7 +145,7 @@ node .agents/scripts/validate-artifact.js gate create-pr .agents/workspace/activ
145
145
  ```
146
146
  下一步(备选)- 跳过监控、直接归档任务:
147
147
  - Claude Code / OpenCode:/complete-task {task-ref}
148
- - Gemini CLI:/agent-infra:complete-task {task-ref}
148
+ - Gemini CLI:/{{project}}:complete-task {task-ref}
149
149
  - Codex CLI:$complete-task {task-ref}
150
150
  ```
151
151
 
@@ -70,6 +70,6 @@ Final user output should include this follow-up path:
70
70
  Next steps:
71
71
  - complete the task after the workflow truly finishes:
72
72
  - Claude Code / OpenCode: /complete-task {task-ref}
73
- - Gemini CLI: /agent-infra:complete-task {task-ref}
73
+ - Gemini CLI: /{{project}}:complete-task {task-ref}
74
74
  - Codex CLI: $complete-task {task-ref}
75
75
  ```
@@ -70,6 +70,6 @@ Milestone 规则:
70
70
  Next steps:
71
71
  - complete the task after the workflow truly finishes:
72
72
  - Claude Code / OpenCode: /complete-task {task-ref}
73
- - Gemini CLI: /agent-infra:complete-task {task-ref}
73
+ - Gemini CLI: /{{project}}:complete-task {task-ref}
74
74
  - Codex CLI: $complete-task {task-ref}
75
75
  ```
@@ -30,7 +30,7 @@ Version stamp rule: when creating or updating `task.md` frontmatter, read `.agen
30
30
 
31
31
  ## Step Start: Capture the Start Time
32
32
 
33
- This skill **creates** task.md, so there is no file to write at the start. Capture `started_at` in memory before running (`date "+%Y-%m-%d %H:%M:%S%:z"`); when writing the Activity Log at the end, **append both lines at once** — the started line uses `started_at`, the done line uses the completion time, both sharing the base action (started line action gets a ` [started]` suffix, note `started`):
33
+ This skill **creates** task.md, so there is no file to write at the start. Capture `started_at` in memory before running (`date "+%Y-%m-%d %H:%M:%S%z" | sed 's/\([+-][0-9][0-9]\)\([0-9][0-9]\)$/\1:\2/'`); when writing the Activity Log at the end, **append both lines at once** — the started line uses `started_at`, the done line uses the completion time, both sharing the base action (started line action gets a ` [started]` suffix, note `started`):
34
34
 
35
35
  ```
36
36
  - {started_at} — **Create Task [started]** by {agent} — started
@@ -109,7 +109,7 @@ priority / effort are required: the AI infers them from the task title and descr
109
109
  Get the current time:
110
110
 
111
111
  ```bash
112
- date "+%Y-%m-%d %H:%M:%S%:z"
112
+ date "+%Y-%m-%d %H:%M:%S%z" | sed 's/\([+-][0-9][0-9]\)\([0-9][0-9]\)$/\1:\2/'
113
113
  ```
114
114
 
115
115
  Update `.agents/workspace/active/{task-id}/task.md`:
@@ -30,7 +30,7 @@ description: >
30
30
 
31
31
  ## 步骤开始:记录开始时间
32
32
 
33
- 本技能会**创建** task.md,开始时尚无文件可写。先在内存记录开始时间 `started_at`(`date "+%Y-%m-%d %H:%M:%S%:z"`);在最后写活动日志时**一次性补两条**——started 行用 `started_at`、done 行用完成时间,二者同基名(started 行 action 加 ` [started]` 后缀、note 用 `started`):
33
+ 本技能会**创建** task.md,开始时尚无文件可写。先在内存记录开始时间 `started_at`(`date "+%Y-%m-%d %H:%M:%S%z" | sed 's/\([+-][0-9][0-9]\)\([0-9][0-9]\)$/\1:\2/'`);在最后写活动日志时**一次性补两条**——started 行用 `started_at`、done 行用完成时间,二者同基名(started 行 action 加 ` [started]` 后缀、note 用 `started`):
34
34
 
35
35
  ```
36
36
  - {started_at} — **Create Task [started]** by {agent} — started
@@ -108,7 +108,7 @@ priority / effort 必填:由 AI 从任务标题与描述推断后填入(候
108
108
  获取当前时间:
109
109
 
110
110
  ```bash
111
- date "+%Y-%m-%d %H:%M:%S%:z"
111
+ date "+%Y-%m-%d %H:%M:%S%z" | sed 's/\([+-][0-9][0-9]\)\([0-9][0-9]\)$/\1:\2/'
112
112
  ```
113
113
 
114
114
  更新 `.agents/workspace/active/{task-id}/task.md`:
@@ -183,7 +183,7 @@ node .agents/scripts/validate-artifact.js gate create-task .agents/workspace/act
183
183
 
184
184
  下一步 - 执行需求分析:
185
185
  - Claude Code / OpenCode:/analyze-task {task-ref}
186
- - Gemini CLI:/agent-infra:analyze-task {task-ref}
186
+ - Gemini CLI:/{{project}}:analyze-task {task-ref}
187
187
  - Codex CLI:$analyze-task {task-ref}
188
188
  ```
189
189
 
@@ -202,7 +202,7 @@ node .agents/scripts/validate-artifact.js gate create-task .agents/workspace/act
202
202
 
203
203
  下一步 - 执行需求分析:
204
204
  - Claude Code / OpenCode:/analyze-task {task-ref}
205
- - Gemini CLI:/agent-infra:analyze-task {task-ref}
205
+ - Gemini CLI:/{{project}}:analyze-task {task-ref}
206
206
  - Codex CLI:$analyze-task {task-ref}
207
207
  ```
208
208
 
@@ -226,7 +226,7 @@ Issue 创建失败:
226
226
 
227
227
  下一步 - 执行需求分析:
228
228
  - Claude Code / OpenCode:/analyze-task {task-ref}
229
- - Gemini CLI:/agent-infra:analyze-task {task-ref}
229
+ - Gemini CLI:/{{project}}:analyze-task {task-ref}
230
230
  - Codex CLI:$analyze-task {task-ref}
231
231
 
232
232
  后续如需平台同步:修复认证/网络/模板问题后,可按 `.agents/rules/create-issue.md` 对当前任务手动执行一次 Issue 创建;或手动创建/查找 Issue,并把 `issue_number` 写入 task.md,后续技能会接管级联同步。
@@ -21,7 +21,7 @@ Import the specified Code Scanning (CodeQL) alert and create a remediation task.
21
21
 
22
22
  ## Step Start: Capture the Start Time
23
23
 
24
- This skill **creates** task.md, so there is no file to write at the start. Capture `started_at` in memory before running (`date "+%Y-%m-%d %H:%M:%S%:z"`); when writing the Activity Log at the end, **append both lines at once** — the started line uses `started_at`, the done line uses the completion time, both sharing the base action (started line action gets a ` [started]` suffix, note `started`):
24
+ This skill **creates** task.md, so there is no file to write at the start. Capture `started_at` in memory before running (`date "+%Y-%m-%d %H:%M:%S%z" | sed 's/\([+-][0-9][0-9]\)\([0-9][0-9]\)$/\1:\2/'`); when writing the Activity Log at the end, **append both lines at once** — the started line uses `started_at`, the done line uses the completion time, both sharing the base action (started line action gets a ` [started]` suffix, note `started`):
25
25
 
26
26
  ```
27
27
  - {started_at} — **Import Codescan [started]** by {agent} — started
@@ -61,7 +61,7 @@ codescan_alert_number: <alert-number>
61
61
  Get the current time:
62
62
 
63
63
  ```bash
64
- date "+%Y-%m-%d %H:%M:%S%:z"
64
+ date "+%Y-%m-%d %H:%M:%S%z" | sed 's/\([+-][0-9][0-9]\)\([0-9][0-9]\)$/\1:\2/'
65
65
  ```
66
66
 
67
67
  Update task.md: `current_step` -> `requirement-analysis`.
@@ -21,7 +21,7 @@ description: >
21
21
 
22
22
  ## 步骤开始:记录开始时间
23
23
 
24
- 本技能会**创建** task.md,开始时尚无文件可写。先在内存记录开始时间 `started_at`(`date "+%Y-%m-%d %H:%M:%S%:z"`);在最后写活动日志时**一次性补两条**——started 行用 `started_at`、done 行用完成时间,二者同基名(started 行 action 加 ` [started]` 后缀、note 用 `started`):
24
+ 本技能会**创建** task.md,开始时尚无文件可写。先在内存记录开始时间 `started_at`(`date "+%Y-%m-%d %H:%M:%S%z" | sed 's/\([+-][0-9][0-9]\)\([0-9][0-9]\)$/\1:\2/'`);在最后写活动日志时**一次性补两条**——started 行用 `started_at`、done 行用完成时间,二者同基名(started 行 action 加 ` [started]` 后缀、note 用 `started`):
25
25
 
26
26
  ```
27
27
  - {started_at} — **Import Codescan [started]** by {agent} — started
@@ -61,7 +61,7 @@ codescan_alert_number: <alert-number>
61
61
  获取当前时间:
62
62
 
63
63
  ```bash
64
- date "+%Y-%m-%d %H:%M:%S%:z"
64
+ date "+%Y-%m-%d %H:%M:%S%z" | sed 's/\([+-][0-9][0-9]\)\([0-9][0-9]\)$/\1:\2/'
65
65
  ```
66
66
 
67
67
  更新 task.md:`current_step` -> `requirement-analysis`。
@@ -112,7 +112,7 @@ Code Scanning 告警 #{alert-number} 已导入。
112
112
 
113
113
  下一步:
114
114
  - Claude Code / OpenCode:/analyze-task {task-ref}
115
- - Gemini CLI:/agent-infra:analyze-task {task-ref}
115
+ - Gemini CLI:/{{project}}:analyze-task {task-ref}
116
116
  - Codex CLI:$analyze-task {task-ref}
117
117
  ```
118
118
 
@@ -21,7 +21,7 @@ Import the specified Dependabot security alert and create a remediation task.
21
21
 
22
22
  ## Step Start: Capture the Start Time
23
23
 
24
- This skill **creates** task.md, so there is no file to write at the start. Capture `started_at` in memory before running (`date "+%Y-%m-%d %H:%M:%S%:z"`); when writing the Activity Log at the end, **append both lines at once** — the started line uses `started_at`, the done line uses the completion time, both sharing the base action (started line action gets a ` [started]` suffix, note `started`):
24
+ This skill **creates** task.md, so there is no file to write at the start. Capture `started_at` in memory before running (`date "+%Y-%m-%d %H:%M:%S%z" | sed 's/\([+-][0-9][0-9]\)\([0-9][0-9]\)$/\1:\2/'`); when writing the Activity Log at the end, **append both lines at once** — the started line uses `started_at`, the done line uses the completion time, both sharing the base action (started line action gets a ` [started]` suffix, note `started`):
25
25
 
26
26
  ```
27
27
  - {started_at} — **Import Dependabot [started]** by {agent} — started
@@ -64,7 +64,7 @@ ghsa_id: <GHSA-ID>
64
64
  Get the current time:
65
65
 
66
66
  ```bash
67
- date "+%Y-%m-%d %H:%M:%S%:z"
67
+ date "+%Y-%m-%d %H:%M:%S%z" | sed 's/\([+-][0-9][0-9]\)\([0-9][0-9]\)$/\1:\2/'
68
68
  ```
69
69
 
70
70
  Update task.md: `current_step` -> `requirement-analysis`.
@@ -21,7 +21,7 @@ description: >
21
21
 
22
22
  ## 步骤开始:记录开始时间
23
23
 
24
- 本技能会**创建** task.md,开始时尚无文件可写。先在内存记录开始时间 `started_at`(`date "+%Y-%m-%d %H:%M:%S%:z"`);在最后写活动日志时**一次性补两条**——started 行用 `started_at`、done 行用完成时间,二者同基名(started 行 action 加 ` [started]` 后缀、note 用 `started`):
24
+ 本技能会**创建** task.md,开始时尚无文件可写。先在内存记录开始时间 `started_at`(`date "+%Y-%m-%d %H:%M:%S%z" | sed 's/\([+-][0-9][0-9]\)\([0-9][0-9]\)$/\1:\2/'`);在最后写活动日志时**一次性补两条**——started 行用 `started_at`、done 行用完成时间,二者同基名(started 行 action 加 ` [started]` 后缀、note 用 `started`):
25
25
 
26
26
  ```
27
27
  - {started_at} — **Import Dependabot [started]** by {agent} — started
@@ -64,7 +64,7 @@ ghsa_id: <GHSA-ID>
64
64
  获取当前时间:
65
65
 
66
66
  ```bash
67
- date "+%Y-%m-%d %H:%M:%S%:z"
67
+ date "+%Y-%m-%d %H:%M:%S%z" | sed 's/\([+-][0-9][0-9]\)\([0-9][0-9]\)$/\1:\2/'
68
68
  ```
69
69
 
70
70
  更新 task.md:`current_step` -> `requirement-analysis`。
@@ -118,7 +118,7 @@ node .agents/scripts/validate-artifact.js gate import-dependabot .agents/workspa
118
118
 
119
119
  下一步:
120
120
  - Claude Code / OpenCode:/analyze-task {task-ref}
121
- - Gemini CLI:/agent-infra:analyze-task {task-ref}
121
+ - Gemini CLI:/{{project}}:analyze-task {task-ref}
122
122
  - Codex CLI:$analyze-task {task-ref}
123
123
  ```
124
124
 
@@ -21,7 +21,7 @@ Import the specified Issue and create a task. Argument: issue number.
21
21
 
22
22
  ## Step Start: Capture the Start Time
23
23
 
24
- This skill **creates** task.md, so there is no file to write at the start. Capture `started_at` in memory before running (`date "+%Y-%m-%d %H:%M:%S%:z"`); when writing the Activity Log at the end, **append both lines at once** — the started line uses `started_at`, the done line uses the completion time, both sharing the base action (started line action gets a ` [started]` suffix, note `started`). The base action must match the actual import scenario:
24
+ This skill **creates** task.md, so there is no file to write at the start. Capture `started_at` in memory before running (`date "+%Y-%m-%d %H:%M:%S%z" | sed 's/\([+-][0-9][0-9]\)\([0-9][0-9]\)$/\1:\2/'`); when writing the Activity Log at the end, **append both lines at once** — the started line uses `started_at`, the done line uses the completion time, both sharing the base action (started line action gets a ` [started]` suffix, note `started`). The base action must match the actual import scenario:
25
25
 
26
26
  ```
27
27
  # Scenario B: new Issue import
@@ -127,7 +127,7 @@ Optional Issue field metadata should preserve recovered or explicit source value
127
127
  Get the current time:
128
128
 
129
129
  ```bash
130
- date "+%Y-%m-%d %H:%M:%S%:z"
130
+ date "+%Y-%m-%d %H:%M:%S%z" | sed 's/\([+-][0-9][0-9]\)\([0-9][0-9]\)$/\1:\2/'
131
131
  ```
132
132
 
133
133
  Update `.agents/workspace/active/{task-id}/task.md`:
@@ -21,7 +21,7 @@ description: >
21
21
 
22
22
  ## 步骤开始:记录开始时间
23
23
 
24
- 本技能会**创建** task.md,开始时尚无文件可写。先在内存记录开始时间 `started_at`(`date "+%Y-%m-%d %H:%M:%S%:z"`);在最后写活动日志时**一次性补两条**——started 行用 `started_at`、done 行用完成时间,二者同基名(started 行 action 加 ` [started]` 后缀、note 用 `started`)。基名必须跟实际导入场景一致:
24
+ 本技能会**创建** task.md,开始时尚无文件可写。先在内存记录开始时间 `started_at`(`date "+%Y-%m-%d %H:%M:%S%z" | sed 's/\([+-][0-9][0-9]\)\([0-9][0-9]\)$/\1:\2/'`);在最后写活动日志时**一次性补两条**——started 行用 `started_at`、done 行用完成时间,二者同基名(started 行 action 加 ` [started]` 后缀、note 用 `started`)。基名必须跟实际导入场景一致:
25
25
 
26
26
  ```
27
27
  # 场景 B:新 Issue 导入
@@ -127,7 +127,7 @@ assigned_to: {当前 AI 代理}
127
127
  获取当前时间:
128
128
 
129
129
  ```bash
130
- date "+%Y-%m-%d %H:%M:%S%:z"
130
+ date "+%Y-%m-%d %H:%M:%S%z" | sed 's/\([+-][0-9][0-9]\)\([0-9][0-9]\)$/\1:\2/'
131
131
  ```
132
132
 
133
133
  更新 `.agents/workspace/active/{task-id}/task.md`:
@@ -195,7 +195,7 @@ Issue #{number} 已导入。
195
195
 
196
196
  下一步 - 执行需求分析:
197
197
  - Claude Code / OpenCode:/analyze-task {task-ref}
198
- - Gemini CLI:/agent-infra:analyze-task {task-ref}
198
+ - Gemini CLI:/{{project}}:analyze-task {task-ref}
199
199
  - Codex CLI:$analyze-task {task-ref}
200
200
  ```
201
201
 
@@ -94,7 +94,7 @@ bash .agents/skills/init-labels/scripts/init-labels.sh
94
94
  ```
95
95
  下一步 - 初始化 Milestones(可选):
96
96
  - Claude Code / OpenCode:/init-milestones
97
- - Gemini CLI:/agent-infra:init-milestones
97
+ - Gemini CLI:/{{project}}:init-milestones
98
98
  - Codex CLI:$init-milestones
99
99
  ```
100
100
 
@@ -30,7 +30,7 @@ bash .agents/skills/init-milestones/scripts/init-milestones.sh "$ARGUMENTS"
30
30
  The script and `.agents/rules/label-milestone-setup.md` are responsible for:
31
31
  - Creating and cleaning up a temporary workspace
32
32
  - Detecting whether `--history` was requested
33
- - Resolving the version baseline from the latest `v*` Git tag, then `package.json`, then defaulting to `0.1.0`
33
+ - Scanning all `v*` Git tags, selecting the highest valid version by SemVer precedence, and using compatibility default `0.1.0` when none is valid, without reading ecosystem manifests
34
34
  - Listing current milestones with the platform-specific milestone query command
35
35
  - Building the desired milestone set and creating only the missing titles
36
36
  - Printing the final execution summary
@@ -50,6 +50,7 @@ When `--history` is present, each historical `vX.Y.Z` tag additionally contribut
50
50
 
51
51
  The summary must include:
52
52
  - Version baseline
53
+ - Version baseline source
53
54
  - Whether `--history` was enabled
54
55
  - Created and skipped milestone counts
55
56
  - Newly created milestone titles
@@ -81,6 +82,6 @@ Next step - initialize labels (optional):
81
82
  - Authentication failed: prompt "the platform CLI is not authenticated"
82
83
  - Repository access failed: prompt "Unable to access the current repository with the platform CLI"
83
84
  - Version detection failed: prompt "Unable to determine current version baseline"
84
- - No `v*` tags found in `--history` mode: prompt "No history tags found matching v*; only standard milestones will be created"
85
+ - No valid SemVer `v*` tags found in `--history` mode: prompt "No valid SemVer history tags found matching v*; only standard milestones will be created"
85
86
  - Permission error: prompt "No permission to manage milestones in this repository"
86
87
  - API rate limit: prompt "platform API rate limit reached, please retry later"
@@ -30,7 +30,7 @@ bash .agents/skills/init-milestones/scripts/init-milestones.sh "$ARGUMENTS"
30
30
  脚本与 `.agents/rules/label-milestone-setup.md` 共同负责:
31
31
  - 创建并清理临时工作目录
32
32
  - 检测是否传入 `--history`
33
- - 按“最新 `v*` Git tag `package.json` 默认 `0.1.0`”解析版本基线
33
+ - 扫描所有 `v*` Git tag,按 SemVer precedence 选择最高合法版本;没有合法版本时使用兼容默认值 `0.1.0`,且不读取任何生态 manifest
34
34
  - 使用平台对应的 milestones 查询命令读取当前里程碑
35
35
  - 构建目标里程碑集合,并且只创建缺失标题
36
36
  - 输出最终执行摘要
@@ -50,6 +50,7 @@ bash .agents/skills/init-milestones/scripts/init-milestones.sh "$ARGUMENTS"
50
50
 
51
51
  摘要必须包含:
52
52
  - 版本基线
53
+ - 版本基线来源
53
54
  - 是否启用 `--history`
54
55
  - 创建与跳过的里程碑数量
55
56
  - 新创建的里程碑标题
@@ -71,7 +72,7 @@ bash .agents/skills/init-milestones/scripts/init-milestones.sh "$ARGUMENTS"
71
72
  ```
72
73
  下一步 - 初始化 Labels(可选):
73
74
  - Claude Code / OpenCode:/init-labels
74
- - Gemini CLI:/agent-infra:init-labels
75
+ - Gemini CLI:/{{project}}:init-labels
75
76
  - Codex CLI:$init-labels
76
77
  ```
77
78
 
@@ -81,6 +82,6 @@ bash .agents/skills/init-milestones/scripts/init-milestones.sh "$ARGUMENTS"
81
82
  - 认证失败:提示 "the platform CLI is not authenticated"
82
83
  - 仓库访问失败:提示 "Unable to access the current repository with the platform CLI"
83
84
  - 版本解析失败:提示 "Unable to determine current version baseline"
84
- - `--history` 模式下未找到任何 `v*` git tags:提示 "No history tags found matching v*; only standard milestones will be created"
85
+ - `--history` 模式下未找到合法 SemVer `v*` git tags:提示 "No valid SemVer history tags found matching v*; only standard milestones will be created"
85
86
  - 权限不足:提示 "No permission to manage milestones in this repository"
86
87
  - API 限流:提示 "platform API rate limit reached, please retry later"
@@ -33,34 +33,171 @@ esac
33
33
 
34
34
  echo "History mode: $history_mode"
35
35
 
36
- current_version=""
37
- latest_tag="$(git tag --list 'v*' --sort=-v:refname | head -1)"
38
-
39
- if [ -n "$latest_tag" ]; then
40
- current_version="${latest_tag#v}"
41
- elif [ -f package.json ]; then
42
- current_version="$(node -p "const version = require('./package.json').version || ''; version.replace(/^v/, '').replace(/-.*/, '')")"
43
- fi
44
-
45
- if [ -z "$current_version" ]; then
46
- current_version="0.1.0"
47
- fi
48
-
49
- major="${current_version%%.*}"
50
- rest="${current_version#*.}"
51
- minor="${rest%%.*}"
52
- patch="${rest#*.}"
53
- patch="${patch%%[^0-9]*}"
36
+ parse_semver_tags() {
37
+ LC_ALL=C awk -v mode="$1" '
38
+ function valid_core_number(value) {
39
+ return value ~ /^(0|[1-9][0-9]*)$/
40
+ }
41
+
42
+ function valid_identifiers(value, prerelease, count, index_, identifiers) {
43
+ if (value == "") return 0
44
+ count = split(value, identifiers, ".")
45
+ for (index_ = 1; index_ <= count; index_++) {
46
+ if (identifiers[index_] !~ /^[0-9A-Za-z-]+$/) return 0
47
+ if (prerelease && identifiers[index_] ~ /^[0-9]+$/ && identifiers[index_] !~ /^(0|[1-9][0-9]*)$/) return 0
48
+ }
49
+ return 1
50
+ }
51
+
52
+ function parse_version(tag, version, main, core, plus_at, dash_at, count) {
53
+ if (substr(tag, 1, 1) != "v") return 0
54
+ version = substr(tag, 2)
55
+ main = version
56
+ parsed_build = ""
57
+ plus_at = index(main, "+")
58
+ if (plus_at > 0) {
59
+ parsed_build = substr(main, plus_at + 1)
60
+ main = substr(main, 1, plus_at - 1)
61
+ if (!valid_identifiers(parsed_build, 0)) return 0
62
+ }
63
+
64
+ parsed_prerelease = ""
65
+ dash_at = index(main, "-")
66
+ if (dash_at > 0) {
67
+ parsed_prerelease = substr(main, dash_at + 1)
68
+ main = substr(main, 1, dash_at - 1)
69
+ if (!valid_identifiers(parsed_prerelease, 1)) return 0
70
+ }
71
+
72
+ count = split(main, core, ".")
73
+ if (count != 3) return 0
74
+ if (!valid_core_number(core[1]) || !valid_core_number(core[2]) || !valid_core_number(core[3])) return 0
75
+
76
+ parsed_tag = tag
77
+ parsed_major = core[1]
78
+ parsed_minor = core[2]
79
+ parsed_patch = core[3]
80
+ return 1
81
+ }
82
+
83
+ function compare_decimal(left, right, index_, left_digit, right_digit) {
84
+ if (length(left) != length(right)) return length(left) > length(right) ? 1 : -1
85
+ for (index_ = 1; index_ <= length(left); index_++) {
86
+ left_digit = substr(left, index_, 1) + 0
87
+ right_digit = substr(right, index_, 1) + 0
88
+ if (left_digit != right_digit) return left_digit > right_digit ? 1 : -1
89
+ }
90
+ return 0
91
+ }
92
+
93
+ function compare_ascii(left, right, alphabet, limit, index_, left_rank, right_rank) {
94
+ alphabet = "+-.0123456789ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz"
95
+ limit = length(left) < length(right) ? length(left) : length(right)
96
+ for (index_ = 1; index_ <= limit; index_++) {
97
+ left_rank = index(alphabet, substr(left, index_, 1))
98
+ right_rank = index(alphabet, substr(right, index_, 1))
99
+ if (left_rank != right_rank) return left_rank > right_rank ? 1 : -1
100
+ }
101
+ if (length(left) == length(right)) return 0
102
+ return length(left) > length(right) ? 1 : -1
103
+ }
104
+
105
+ function compare_prerelease(left, right, left_count, right_count, limit, index_, comparison, left_numeric, right_numeric, left_ids, right_ids) {
106
+ if (left == "" || right == "") {
107
+ if (left == right) return 0
108
+ return left == "" ? 1 : -1
109
+ }
110
+
111
+ left_count = split(left, left_ids, ".")
112
+ right_count = split(right, right_ids, ".")
113
+ limit = left_count < right_count ? left_count : right_count
114
+ for (index_ = 1; index_ <= limit; index_++) {
115
+ left_numeric = left_ids[index_] ~ /^[0-9]+$/
116
+ right_numeric = right_ids[index_] ~ /^[0-9]+$/
117
+ if (left_numeric && right_numeric) {
118
+ comparison = compare_decimal(left_ids[index_], right_ids[index_])
119
+ } else if (left_numeric != right_numeric) {
120
+ comparison = left_numeric ? -1 : 1
121
+ } else {
122
+ comparison = compare_ascii(left_ids[index_], right_ids[index_])
123
+ }
124
+ if (comparison != 0) return comparison
125
+ }
126
+
127
+ if (left_count == right_count) return 0
128
+ return left_count > right_count ? 1 : -1
129
+ }
130
+
131
+ function candidate_is_higher( comparison) {
132
+ comparison = compare_decimal(parsed_major, best_major)
133
+ if (comparison != 0) return comparison > 0
134
+ comparison = compare_decimal(parsed_minor, best_minor)
135
+ if (comparison != 0) return comparison > 0
136
+ comparison = compare_decimal(parsed_patch, best_patch)
137
+ if (comparison != 0) return comparison > 0
138
+ comparison = compare_prerelease(parsed_prerelease, best_prerelease)
139
+ if (comparison != 0) return comparison > 0
140
+ return compare_ascii(parsed_tag, best_tag) > 0
141
+ }
142
+
143
+ function increment_decimal(value, index_, digit, output) {
144
+ output = ""
145
+ for (index_ = length(value); index_ >= 1; index_--) {
146
+ digit = substr(value, index_, 1) + 0
147
+ if (digit < 9) return substr(value, 1, index_ - 1) (digit + 1) output
148
+ output = "0" output
149
+ }
150
+ return "1" output
151
+ }
152
+
153
+ parse_version($0) {
154
+ if (mode == "history") {
155
+ printf "%s\t%s\t%s\n", parsed_major, parsed_minor, parsed_patch
156
+ next
157
+ }
158
+
159
+ if (!have_best || candidate_is_higher()) {
160
+ have_best = 1
161
+ best_tag = parsed_tag
162
+ best_major = parsed_major
163
+ best_minor = parsed_minor
164
+ best_patch = parsed_patch
165
+ best_prerelease = parsed_prerelease
166
+ }
167
+ }
168
+
169
+ END {
170
+ if (mode == "history") exit
171
+ if (!have_best) {
172
+ best_tag = "-"
173
+ best_major = "0"
174
+ best_minor = "1"
175
+ best_patch = "0"
176
+ }
177
+ printf "%s\t%s\t%s\t%s\t%s\n", best_tag, best_major, best_minor, best_patch, increment_decimal(best_patch)
178
+ }
179
+ '
180
+ }
181
+
182
+ selection="$(git tag --list 'v*' | parse_semver_tags select)"
183
+ previous_ifs="$IFS"
184
+ IFS="$(printf '\t')" read -r selected_tag major minor patch next_patch <<EOF
185
+ $selection
186
+ EOF
187
+ IFS="$previous_ifs"
54
188
 
55
- if ! printf '%s %s %s\n' "$major" "$minor" "$patch" | grep -Eq '^[0-9]+ [0-9]+ [0-9]+$'; then
56
- echo "Unable to determine current version baseline"
57
- exit 1
189
+ current_version="$major.$minor.$patch"
190
+ if [ "$selected_tag" = "-" ]; then
191
+ version_source="compatibility default"
192
+ else
193
+ version_source="git tag $selected_tag"
58
194
  fi
59
195
 
60
196
  line_milestone="$major.$minor.x"
61
- next_version="$major.$minor.$((patch + 1))"
197
+ next_version="$major.$minor.$next_patch"
62
198
 
63
199
  echo "Detected version baseline: $current_version"
200
+ echo "Version baseline source: $version_source"
64
201
  echo "Line milestone: $line_milestone"
65
202
  echo "Next version milestone: $next_version"
66
203
 
@@ -80,26 +217,12 @@ $next_version Issues that we want to release in v$next_version. open
80
217
  EOF
81
218
 
82
219
  if [ "$history_mode" = "true" ]; then
83
- git tag --list 'v*' --sort=v:refname > "$tmpdir/history-tags.txt"
220
+ git tag --list 'v*' | parse_semver_tags history > "$tmpdir/history-versions.tsv"
84
221
 
85
- if [ ! -s "$tmpdir/history-tags.txt" ]; then
86
- echo "No history tags found matching v*; only standard milestones will be created."
222
+ if [ ! -s "$tmpdir/history-versions.tsv" ]; then
223
+ echo "No valid SemVer history tags found matching v*; only standard milestones will be created."
87
224
  else
88
- while IFS= read -r tag; do
89
- [ -n "$tag" ] || continue
90
-
91
- ver="${tag#v}"
92
- h_major="${ver%%.*}"
93
- h_rest="${ver#*.}"
94
- h_minor="${h_rest%%.*}"
95
- h_patch="${h_rest#*.}"
96
- h_patch="${h_patch%%[^0-9]*}"
97
-
98
- if ! printf '%s %s %s\n' "$h_major" "$h_minor" "$h_patch" | grep -Eq '^[0-9]+ [0-9]+ [0-9]+$'; then
99
- echo "Skip non-semver tag: $tag"
100
- continue
101
- fi
102
-
225
+ while IFS="$(printf '\t')" read -r h_major h_minor h_patch; do
103
226
  printf '%s\t%s\t%s\n' \
104
227
  "$h_major.$h_minor.x" \
105
228
  "Issues that we want to resolve in $h_major.$h_minor line." \
@@ -109,7 +232,7 @@ if [ "$history_mode" = "true" ]; then
109
232
  "$h_major.$h_minor.$h_patch" \
110
233
  "Issues that we want to release in v$h_major.$h_minor.$h_patch." \
111
234
  "closed" >> "$tmpdir/desired.tsv"
112
- done < "$tmpdir/history-tags.txt"
235
+ done < "$tmpdir/history-versions.tsv"
113
236
  fi
114
237
  fi
115
238
 
@@ -143,6 +266,7 @@ echo "GitHub Milestones initialized."
143
266
  echo
144
267
  echo "Summary:"
145
268
  echo "- Version baseline: $current_version"
269
+ echo "- Version baseline source: $version_source"
146
270
  echo "- History mode: $history_mode"
147
271
  echo "- Created milestones: $created_count"
148
272
  echo "- Skipped existing milestones: $skipped_count"
@@ -117,7 +117,7 @@ Create `.agents/workspace/active/{task-id}/{plan-artifact}`.
117
117
  Get the current time:
118
118
 
119
119
  ```bash
120
- date "+%Y-%m-%d %H:%M:%S%:z"
120
+ date "+%Y-%m-%d %H:%M:%S%z" | sed 's/\([+-][0-9][0-9]\)\([0-9][0-9]\)$/\1:\2/'
121
121
  ```
122
122
 
123
123
  Update `.agents/workspace/active/{task-id}/task.md`:
@@ -116,7 +116,7 @@ tail .agents/workspace/active/{task-id}/task.md
116
116
  获取当前时间:
117
117
 
118
118
  ```bash
119
- date "+%Y-%m-%d %H:%M:%S%:z"
119
+ date "+%Y-%m-%d %H:%M:%S%z" | sed 's/\([+-][0-9][0-9]\)\([0-9][0-9]\)$/\1:\2/'
120
120
  ```
121
121
 
122
122
  更新 `.agents/workspace/active/{task-id}/task.md`:
@@ -183,7 +183,7 @@ node .agents/scripts/validate-artifact.js gate plan-task .agents/workspace/activ
183
183
 
184
184
  下一步 - 审查技术方案:
185
185
  - Claude Code / OpenCode:/review-plan {task-ref}
186
- - Gemini CLI:/agent-infra:review-plan {task-ref}
186
+ - Gemini CLI:/{{project}}:review-plan {task-ref}
187
187
  - Codex CLI:$review-plan {task-ref}
188
188
  ```
189
189
 
@@ -95,7 +95,7 @@ Write only files that were actually recovered from Issue comments. Do not invent
95
95
  Get the current time:
96
96
 
97
97
  ```bash
98
- date "+%Y-%m-%d %H:%M:%S%:z"
98
+ date "+%Y-%m-%d %H:%M:%S%z" | sed 's/\([+-][0-9][0-9]\)\([0-9][0-9]\)$/\1:\2/'
99
99
  ```
100
100
 
101
101
  Update the restored `task.md`:
@@ -94,7 +94,7 @@ description: >
94
94
  获取当前时间:
95
95
 
96
96
  ```bash
97
- date "+%Y-%m-%d %H:%M:%S%:z"
97
+ date "+%Y-%m-%d %H:%M:%S%z" | sed 's/\([+-][0-9][0-9]\)\([0-9][0-9]\)$/\1:\2/'
98
98
  ```
99
99
 
100
100
  更新恢复出的 `task.md`:
@@ -73,7 +73,7 @@ Create `.agents/workspace/active/{task-id}/{review-artifact}`.
73
73
  Get the current time:
74
74
 
75
75
  ```bash
76
- date "+%Y-%m-%d %H:%M:%S%:z"
76
+ date "+%Y-%m-%d %H:%M:%S%z" | sed 's/\([+-][0-9][0-9]\)\([0-9][0-9]\)$/\1:\2/'
77
77
  ```
78
78
 
79
79
  Set `current_step` to `requirement-analysis-review`, refresh task metadata, and append:
@@ -79,7 +79,7 @@ tail .agents/workspace/active/{task-id}/task.md
79
79
  获取当前时间:
80
80
 
81
81
  ```bash
82
- date "+%Y-%m-%d %H:%M:%S%:z"
82
+ date "+%Y-%m-%d %H:%M:%S%z" | sed 's/\([+-][0-9][0-9]\)\([0-9][0-9]\)$/\1:\2/'
83
83
  ```
84
84
 
85
85
  更新 task.md: