paseo-req-kit 0.0.0-stage → 1.7.0-beta.3

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 (130) hide show
  1. package/CHANGELOG.md +217 -0
  2. package/LICENSE +21 -0
  3. package/README.md +141 -2
  4. package/SCOPE.md +11 -0
  5. package/bin/locate.mjs +46 -0
  6. package/bin/req-doctor.mjs +21 -0
  7. package/bin/req.mjs +175 -0
  8. package/bin/start-pipeline +21 -0
  9. package/bin/start-pipeline.mjs +22 -0
  10. package/config.example.json +101 -0
  11. package/contracts/README.md +18 -0
  12. package/contracts/feature-files.md +87 -0
  13. package/contracts/notifier-event.md +71 -0
  14. package/contracts/result-file.md +17 -0
  15. package/contracts/spec.md +34 -0
  16. package/contracts/state.md +44 -0
  17. package/contracts/verify.md +39 -0
  18. package/docs/adr/0001-step-agents-under-origin-chat.md +15 -0
  19. package/docs/adr/0002-no-directory-switch-in-chat.md +15 -0
  20. package/docs/adr/0003-script-engine-not-hub.md +15 -0
  21. package/docs/adr/0004-result-files.md +15 -0
  22. package/docs/adr/0005-no-default-branch-local-commits-only.md +15 -0
  23. package/docs/adr/0006-skill-install-targets.md +15 -0
  24. package/docs/adr/0007-own-interview-skill.md +15 -0
  25. package/docs/adr/0008-entries-do-not-call-entries.md +15 -0
  26. package/docs/adr/0009-versioned-install-layout.md +15 -0
  27. package/docs/adr/0010-generated-feature-overview.md +15 -0
  28. package/docs/adr/0011-resume-after-completion.md +15 -0
  29. package/docs/adr/0012-review-panel.md +18 -0
  30. package/docs/adr/0013-no-release-tooling.md +15 -0
  31. package/docs/adr/0014-notifier-slot.md +19 -0
  32. package/docs/adr/0015-incremental-continue.md +17 -0
  33. package/docs/adr/0016-upgrade-from-tags.md +19 -0
  34. package/docs/adr/0017-use-paseo-capabilities.md +18 -0
  35. package/docs/adr/0018-own-worktree-option.md +21 -0
  36. package/docs/adr/0019-parallel-orchestration.md +21 -0
  37. package/docs/adr/0020-scheduling-through-the-chat.md +21 -0
  38. package/docs/adr/0021-npm-version-manager.md +19 -0
  39. package/docs/adr/0022-develop-and-verify-phases.md +32 -0
  40. package/docs/adr/README.md +26 -0
  41. package/docs/guide//344/275/277/347/224/250/350/200/205/346/214/207/345/215/227.md +78 -0
  42. package/docs/guide//345/256/211/350/243/205/344/270/216/345/215/207/347/272/247.md +348 -0
  43. package/docs/guide//347/273/264/346/212/244/350/200/205/346/214/207/345/215/227.md +85 -0
  44. package/docs/guide//351/241/271/347/233/256/345/256/232/345/210/266/344/270/216/350/277/220/350/241/214/350/247/204/345/210/231.md +251 -0
  45. package/engine/prompts/00-shared-context.md +100 -0
  46. package/engine/prompts/02-spec-review.md +46 -0
  47. package/engine/prompts/03-design.md +50 -0
  48. package/engine/prompts/03a-design-proposal.md +30 -0
  49. package/engine/prompts/04-design-review.md +72 -0
  50. package/engine/prompts/04b-design-revise.md +34 -0
  51. package/engine/prompts/05-implement.md +66 -0
  52. package/engine/prompts/06-code-review.md +66 -0
  53. package/engine/prompts/07-review-fix.md +41 -0
  54. package/engine/prompts/07b-handoff.md +45 -0
  55. package/engine/prompts/08-service-start.md +59 -0
  56. package/engine/prompts/09-verify.md +90 -0
  57. package/engine/prompts/10-defect-fix.md +41 -0
  58. package/engine/prompts/10b-reverify.md +43 -0
  59. package/engine/prompts/11-report.md +93 -0
  60. package/engine/prompts/browser-verify.md +13 -0
  61. package/engine/prompts/incremental.md +21 -0
  62. package/engine/prompts/panel-member.md +38 -0
  63. package/engine/prompts/paseo-services.md +9 -0
  64. package/engine/prompts/verify-deployed.md +14 -0
  65. package/engine/src/activity.ts +87 -0
  66. package/engine/src/cli-args.ts +204 -0
  67. package/engine/src/config.ts +479 -0
  68. package/engine/src/configure.ts +237 -0
  69. package/engine/src/control.ts +230 -0
  70. package/engine/src/daemon-check.ts +104 -0
  71. package/engine/src/daemon-version.ts +66 -0
  72. package/engine/src/digest.ts +133 -0
  73. package/engine/src/doctor.ts +435 -0
  74. package/engine/src/eval.ts +324 -0
  75. package/engine/src/features.ts +268 -0
  76. package/engine/src/git.ts +30 -0
  77. package/engine/src/launch.ts +405 -0
  78. package/engine/src/locations.ts +55 -0
  79. package/engine/src/main.ts +313 -0
  80. package/engine/src/messages.ts +308 -0
  81. package/engine/src/notifiers.ts +76 -0
  82. package/engine/src/notify-test.ts +97 -0
  83. package/engine/src/paseo-json.ts +73 -0
  84. package/engine/src/paseo-profiles.ts +133 -0
  85. package/engine/src/paseo-runtime.ts +437 -0
  86. package/engine/src/paths.ts +10 -0
  87. package/engine/src/pipeline.ts +1126 -0
  88. package/engine/src/preflight.ts +298 -0
  89. package/engine/src/prompts.ts +72 -0
  90. package/engine/src/queue.ts +61 -0
  91. package/engine/src/runtime-loader.ts +14 -0
  92. package/engine/src/runtime.ts +155 -0
  93. package/engine/src/schedule-time.ts +51 -0
  94. package/engine/src/smoke-test.ts +202 -0
  95. package/engine/src/spec-review.ts +100 -0
  96. package/engine/src/state.ts +278 -0
  97. package/engine/src/steps.ts +242 -0
  98. package/engine/src/usage.ts +67 -0
  99. package/engine/src/worktree.ts +72 -0
  100. package/install.mjs +928 -0
  101. package/notifiers/im-template.mjs +58 -0
  102. package/package.json +67 -4
  103. package/principles/INDEX.md +11 -0
  104. package/skills/acceptance-criteria/SKILL.md +52 -0
  105. package/skills/principle-delete-before-add/SKILL.md +33 -0
  106. package/skills/principle-dont-block-on-humans/SKILL.md +35 -0
  107. package/skills/principle-fix-root-cause/SKILL.md +33 -0
  108. package/skills/principle-prove-it-works/SKILL.md +33 -0
  109. package/skills/principle-report-honestly/SKILL.md +33 -0
  110. package/skills/principle-speak-to-reader/SKILL.md +33 -0
  111. package/skills/principle-this-requirement-only/SKILL.md +33 -0
  112. package/skills/req/SKILL.md +99 -0
  113. package/skills/req/playbooks/accept.md +65 -0
  114. package/skills/req/playbooks/change.md +51 -0
  115. package/skills/req/playbooks/incident.md +55 -0
  116. package/skills/req/playbooks/new.md +83 -0
  117. package/skills/req/playbooks/small.md +48 -0
  118. package/skills/req/playbooks/status.md +39 -0
  119. package/skills/req/playbooks/takeover.md +51 -0
  120. package/skills/req/playbooks/verify.md +57 -0
  121. package/skills/req-doctor/SKILL.md +36 -0
  122. package/skills/req-retro/SKILL.md +79 -0
  123. package/skills/req-setup/SKILL.md +101 -0
  124. package/skills/req-setup/templates/paseo/copy-local-files.mjs +32 -0
  125. package/skills/req-setup/templates/paseo/with-port.mjs +36 -0
  126. package/skills/requirement-interview/SKILL.md +94 -0
  127. package/skills/requirement-kickoff/SKILL.md +17 -0
  128. package/skills/result-report/SKILL.md +34 -0
  129. package/skills/spec-writing/SKILL.md +41 -0
  130. package/skills/spec-writing/spec-template.md +106 -0
@@ -0,0 +1,32 @@
1
+ #!/usr/bin/env node
2
+ // Written into the project by req-kit's /req-setup. Copies local files that are not committed
3
+ // (for example .env) from the checkout a new Paseo worktree was created from, the same way on
4
+ // macOS, Linux and Windows. Files that do not exist there, or already exist here, are skipped.
5
+ //
6
+ // paseo.json: "worktree": { "setup": ["npm ci", "node scripts/paseo/copy-local-files.mjs .env"] }
7
+
8
+ import fs from "node:fs";
9
+ import path from "node:path";
10
+
11
+ const source = process.env.PASEO_SOURCE_CHECKOUT_PATH;
12
+ const files = process.argv.slice(2);
13
+ if (!source) {
14
+ console.log("没有环境变量 PASEO_SOURCE_CHECKOUT_PATH(不是 Paseo 新建 worktree 时运行的),跳过。");
15
+ process.exit(0);
16
+ }
17
+ for (const file of files) {
18
+ const from = path.resolve(source, file);
19
+ const to = path.resolve(process.cwd(), file);
20
+ if (path.resolve(from) === path.resolve(to)) continue;
21
+ if (!fs.existsSync(from)) {
22
+ console.log(`跳过 ${file}:来源目录中没有`);
23
+ continue;
24
+ }
25
+ if (fs.existsSync(to)) {
26
+ console.log(`跳过 ${file}:这里已经有了`);
27
+ continue;
28
+ }
29
+ fs.mkdirSync(path.dirname(to), { recursive: true });
30
+ fs.cpSync(from, to, { recursive: true });
31
+ console.log(`已复制 ${file}`);
32
+ }
@@ -0,0 +1,36 @@
1
+ #!/usr/bin/env node
2
+ // Written into the project by req-kit's /req-setup. Runs a command with {PORT} replaced by
3
+ // the port Paseo assigned (PASEO_PORT), the same way on macOS, Linux and Windows, whatever
4
+ // shell Paseo uses there (bash, sh, cmd.exe). Also sets PORT for programs that read it.
5
+ //
6
+ // paseo.json: "command": "node scripts/paseo/with-port.mjs npm run dev -- --port {PORT}"
7
+ // by hand: PASEO_PORT=4100 node scripts/paseo/with-port.mjs npm run dev -- --port {PORT}
8
+
9
+ import { spawn } from "node:child_process";
10
+
11
+ const args = process.argv.slice(2);
12
+ if (args.length === 0) {
13
+ console.error("用法:node scripts/paseo/with-port.mjs <命令> [参数…](参数中的 {PORT} 换成环境变量 PASEO_PORT)");
14
+ process.exit(2);
15
+ }
16
+ const port = process.env.PASEO_PORT ?? process.env.PORT;
17
+ if (!port && args.some((a) => a.includes("{PORT}"))) {
18
+ console.error("没有环境变量 PASEO_PORT:它由 Paseo 提供,手工运行时请自己设置。");
19
+ process.exit(2);
20
+ }
21
+ const resolved = args.map((a) => (port ? a.replaceAll("{PORT}", port) : a));
22
+ // npm, npx and other .cmd shims need a shell on Windows.
23
+ const windows = process.platform === "win32";
24
+ const child = spawn(resolved[0], resolved.slice(1).map((a) => (windows && /[\s"]/.test(a) ? `"${a.replace(/"/g, '\\"')}"` : a)), {
25
+ stdio: "inherit",
26
+ shell: windows,
27
+ env: port ? { ...process.env, PORT: port } : process.env,
28
+ });
29
+ for (const signal of ["SIGINT", "SIGTERM", "SIGHUP"]) {
30
+ process.on(signal, () => child.kill(signal));
31
+ }
32
+ child.on("error", (error) => {
33
+ console.error(`无法启动 ${resolved[0]}:${error.message}`);
34
+ process.exit(127);
35
+ });
36
+ child.on("exit", (code, signal) => process.exit(code ?? (signal ? 1 : 0)));
@@ -0,0 +1,94 @@
1
+ ---
2
+ name: requirement-interview
3
+ description: req-kit 方法:通过一次一问、带选项和推荐的访谈,把一个需求谈到"换一个人来做也会做出同一个东西"的程度,并边谈边记录到 alignment.md 和 GLOSSARY.md。由 /req 的手册调用;单独使用时也适用于任何需求澄清。
4
+ ---
5
+
6
+ # 需求访谈
7
+
8
+ ## 目标
9
+
10
+ 把需求谈到"换一个人来做,也会做出同一个东西"的清晰程度。访谈的结果之后交给无人值守的开发流水线,流水线里没有人能再回头问,所以**现在没问清楚的地方,后面只能靠猜**。
11
+
12
+ ## 对面是谁
13
+
14
+ 需求方通常是测试、产品经理或项目经理:有一定技术背景,熟悉接口、字段、状态、测试用例、测试环境这些概念,但不读代码。据此:
15
+
16
+ - 可以直接用他们熟悉的概念提问,例如"这个接口失败时返回什么错误码""列表要不要按创建时间倒序"。
17
+ - 不问代码层面的选择(用哪个框架、怎么拆模块、同步还是异步)。这些由你决定,记入 spec 的"技术假设"。
18
+ - 他们往往最清楚异常流程、测试数据和环境,这些要重点问。
19
+
20
+ ## 开口之前
21
+
22
+ 1. 先读项目里已有的资料:`GLOSSARY.md`(术语表;较早的项目可能叫 `CONTEXT.md`)、`docs/adr/`(已做的决定)、`README`、`CLAUDE.md` / `AGENTS.md`、`.requirement-pipeline/project-notes.md`,以及与需求相关的代码和现有页面、接口。
23
+ 2. 能从代码和文档里得到答案的事,不拿去问。可以说"我看到现在的列表是按创建时间倒序的,新功能沿用这个顺序,对吗?",把发现变成一个确认题。
24
+
25
+ ## 怎么问
26
+
27
+ **先听,再复述。** 请对方用自己的话把想要的东西讲一遍。用两三句话复述你的理解,确认后再往下问。
28
+
29
+ **一次只问一个问题。** 每个问题给 2–4 个选项,把你推荐的放在第一个并说明理由。环境里有选择题式的提问工具就用它,否则用带编号的文字选项。对方说"你定"时,采用推荐项,记为假设。
30
+
31
+ **问结果,不问手段。** 问"提交之后,谁应该在多久之内看到这条记录",不问"要不要用消息队列"。
32
+
33
+ **技术限制翻译成可见后果。** 不说"这需要改表结构",而说"这样做的话,以前的历史订单不会带上这个信息,只有新订单才有。可以接受吗?"
34
+
35
+ **用具体例子提问。** "张三周五下午 6 点提交了申请,审批人周一才上班,这期间张三看到的状态是什么?"比"审批超时怎么处理"更好回答。
36
+
37
+ **追问到目的。** 对方说"加一个导出按钮"时,问清楚导出之后拿去做什么。真正的需求常常是另一件事。
38
+
39
+ **主动问对方没想到的情况:**
40
+ - 出错和中断:输入不合法、提交到一半关掉、重复提交、依赖的服务不可用
41
+ - 反悔:能不能撤销、修改、删除,谁可以
42
+ - 权限:谁能看、谁能改、谁不能看
43
+ - 边界:数量上限、时间期限、空值、超长输入、并发
44
+ - 已有的数据和进行中的业务怎么办
45
+ - 测试:用什么测试数据、在哪个环境验证、有没有现成的测试账号或测试替身
46
+ - 这次明确不做什么
47
+
48
+ **每条需求都问"怎么算做对了"。** 要一个可以实际检查的答案,它会成为验收标准(写法见 `{{REQ_KIT_ROOT}}/skills/acceptance-criteria/SKILL.md`)。
49
+
50
+ **控制节奏。** 每谈完一个主题,用一两句话小结"已经定了什么、还剩什么"。对方的说法与现有文档或系统行为矛盾时,直接指出并请对方选择。
51
+
52
+ **区分"必须问"和"可以假设"。** 猜错会做出错误东西的,一定问;其余的按最合理的理解假设并记录(见原则 `principle-dont-block-on-humans`)。
53
+
54
+ ## 边谈边记
55
+
56
+ 在功能目录下维护 `alignment.md`,每定下一件事就追加一条,不要等到最后再回忆:
57
+
58
+ ```markdown
59
+ ## <主题>
60
+ - 问题:<问题>
61
+ - 结论:<定下来的答案>
62
+ - 理由 / 被否的选项:<一句话>
63
+ - 来源:需求方明确确认 / 需求方说"你定"(记为假设)/ 从现有代码或文档得出
64
+ ```
65
+
66
+ **术语。** 出现新的业务或领域术语,或者发现同一个词在不同地方意思不同时,写入仓库根目录的 `GLOSSARY.md`(不存在就创建):
67
+
68
+ ```markdown
69
+ ## <术语>
70
+ <在本项目中的确切含义。一两句话。>
71
+ - 不要与"<容易混淆的词>"混用:<区别>
72
+ ```
73
+
74
+ 项目里已有 `CONTEXT.md`(旧名)时,先读它;新增的术语仍写入 `GLOSSARY.md`,两者是否合并由开发同事决定。
75
+
76
+ **重要决定。** 影响以后很多需求、并且不容易推翻的决定(例如"订单号对外展示时一律脱敏"),在 `docs/adr/` 下新建一条记录:`<四位编号>-<英文短名>.md`,写明背景、决定、理由。不确定是否算重要时,不写。
77
+
78
+ ## 什么时候可以结束
79
+
80
+ **快速档**:要改什么、改成什么样、不改什么、每条验收标准,都有了结论。
81
+
82
+ **标准档**:下面每一项都有了结论,或被明确标为"假设"或"本次不做":
83
+
84
+ - 要解决的问题,以及做成之后怎么衡量
85
+ - 谁会用,在什么场景下用
86
+ - 主流程的每一步
87
+ - 规则(计算方式、状态变化、限制条件)
88
+ - 出错、反悔、权限、边界、已有数据
89
+ - 测试数据和验证环境
90
+ - 本次不做的范围
91
+ - 每条需求的验收标准
92
+ - 优先级:哪些必须有,哪些可以以后再说
93
+
94
+ 还有只有需求方能回答、且答错会导致做错东西的问题时,继续问,不要带着它进入下一步。
@@ -0,0 +1,17 @@
1
+ ---
2
+ name: requirement-kickoff
3
+ description: 旧入口,已改名为 /req。用户输入 /requirement-kickoff 时使用:提示改用 /req,并按 /req 继续处理。
4
+ metadata:
5
+ opencode/slash: "true"
6
+ ---
7
+
8
+ # 旧入口:/requirement-kickoff
9
+
10
+ 用户的话:$ARGUMENTS
11
+
12
+ 这个入口已经改名为 `/req`(req-kit {{REQ_KIT_VERSION}}),功能相同,并且新增了小改动、查看进度、暂停和继续等场景。
13
+
14
+ 1. 先用一句话告诉用户:以后请输入 `/req`(Pi 中为 `/skill:req`),这次照常处理。
15
+ 2. 然后读取 `{{REQ_KIT_ROOT}}/skills/req/SKILL.md`,把用户的话当作 `/req` 的输入,按它的说明继续。
16
+
17
+ 这个过渡入口会在 req-kit 2.0 中移除。
@@ -0,0 +1,34 @@
1
+ ---
2
+ name: result-report
3
+ description: req-kit 方法:把流水线的通知、状态和各步骤产物整理成需求方能核对的结果说明,结论先行,分清已验证和未验证,写明证据位置和下一步。由 /req 转述进度、通知、完成报告和接手时调用。
4
+ ---
5
+
6
+ # 结果说明
7
+
8
+ 需求方(测试、产品、项目经理)要根据你的话做决定:是否验收、是否需要回答问题、是否找开发同事。说清楚,并且让他们能自己核对。
9
+
10
+ ## 写法
11
+
12
+ 1. **结论先行。** 第一句话就是结论:做到哪一步了、成没成、要不要他们做什么。
13
+ 2. **分清三类。** 已验证(有运行证据)、未验证(说明原因)、有问题(现象和影响)。不要把未验证的说成完成。
14
+ 3. **给出证据位置。** 结论来自哪个文件的哪一节,例如"验收对照表见 report.md 第 3 节""AC-2.1 的测试输出见 verification.md"。能用命令复核的,给出命令。
15
+ 4. **讲需求和结果,不讲实现。** 可以说接口、字段、页面、测试用例;不说类名、函数名、提交号,除非对方问起。
16
+ 5. **下一步具体到动作。** "请按 report.md 的验收对照表逐条试用,AC-3.2 需要用测试账号 B 登录",而不是"请验收"。
17
+ 6. **长度。** 进展一句话;状态两三句;完成或中断不超过 8 行,详细内容指向文件。
18
+
19
+ ## 常见场景
20
+
21
+ - **进展通知**:一句话,例如"方案已经定了(审核 1 轮),开始写代码"。
22
+ - **查看进度**:现在在做什么、已完成哪些、进行了多久;有等待决定或遗留问题时一并说明。
23
+ - **中断**:在哪一步、原因、日志位置;对方能自己处理的(例如测试服务没启动)给出做法,否则建议找开发同事;处理后怎么继续。
24
+ - **完成**:结论(可以验收 / 有遗留问题 / 未完成),最重要的一两条遗留问题,需要他们确认的决定有几条,下一步做什么。
25
+ - **接手**:这个需求要做什么(一两句)、现在在哪个阶段、有哪些待决事项、接下来建议做什么。
26
+
27
+ ## 数据来源
28
+
29
+ 以文件为准,不凭记忆:
30
+
31
+ - 进度:`start-pipeline --status` 的输出、`progress.md`
32
+ - 结论和证据:`report.md`、`verification.md`、`code-review.md`
33
+ - 需要人确认的决定:`report.md` 的"需要你确认的决定"、`decisions.tsv` 中 `needs_human` 为 `yes` 的行
34
+ - 需求和变更:`spec.md`、`changes.md`;验收结果:`acceptance.md`
@@ -0,0 +1,41 @@
1
+ ---
2
+ name: spec-writing
3
+ description: req-kit 方法:把访谈记录(alignment.md)整理成标准需求说明 spec.md,自查后给需求方一份 10 行以内的摘要请其确认,确认后标记为"已确认"并提交。由 /req 的手册调用。
4
+ ---
5
+
6
+ # 需求说明(spec)
7
+
8
+ spec 是开发流水线判断"要做什么"的唯一依据。流水线的每一步都会引用它的编号(FR-n、AC-n.m),最终报告也按它逐条对照。
9
+
10
+ ## 写
11
+
12
+ 1. 按模板 `{{REQ_KIT_ROOT}}/skills/spec-writing/spec-template.md` 的结构,把 `alignment.md` 的内容整理成 `<功能目录>/spec.md`。
13
+ 2. 填好顶部的几行。流水线只读其中三行,写法要保持原样:
14
+ - `- 状态:草稿`(确认后改为 `- 状态:已确认(<日期>)`)
15
+ - `- 档位:标准` 或 `- 档位:快速`
16
+ - `- 执行方式:分阶段` 或 `- 执行方式:只做研发`:只在用户选了这两种时写;连续(默认)不写这一行
17
+ 其余几行(类型、版本、格式)给人和 `/req` 看。新需求的版本是 1,每次修改需求加 1。
18
+ 3. 快速档可以省略与这次改动无关的章节,但"范围""功能需求与验收标准""假设"必须有。
19
+ 4. 写作要求:
20
+ - 只写"要什么"和"怎么算做对",不写"怎么实现"。技术上的想法只进入"技术假设"一节。
21
+ - 每条功能需求有编号(FR-1、FR-2…),每条验收标准有编号(AC-1.1、AC-1.2…),写法见 `acceptance-criteria`(`{{REQ_KIT_ROOT}}/skills/acceptance-criteria/SKILL.md`)。
22
+ - 没谈到的内容不要自己补。需要补的,回去问,或写进"假设"并说明依据。
23
+ - 术语与仓库的 `GLOSSARY.md` 一致。
24
+
25
+ ## 自查
26
+
27
+ 写完后逐项检查,发现问题就改:
28
+
29
+ - 每条 FR 至少有一条可以实际检查的 AC
30
+ - 异常和边界情况都有对应的 AC,而不是只有正常流程
31
+ - 没有"快速""友好""合理"这类无法检查的词,除非给出了具体标准
32
+ - 各条需求之间没有互相矛盾
33
+ - "测试与验证"一节写明了测试数据和验证环境(快速档可以只写一句)
34
+ - "待确认问题"一节为空。不为空就回去问
35
+
36
+ ## 确认
37
+
38
+ 1. 给需求方一份 10 行以内的摘要:会做什么、不做什么、有哪些假设需要他们知情、他们之后会怎么验收。告诉他们完整文件的位置,愿意的话可以直接打开看。
39
+ 2. 请他们确认。提出修改时,回到访谈,改完再自查、再确认。
40
+ 3. 确认后,把顶部改为 `- 状态:已确认(<日期>)`。没有确认的 spec 不要标为"已确认"。
41
+ 4. 如果是 git 仓库,把功能目录、`GLOSSARY.md` 和 `docs/adr/` 中本次的改动提交到当前分支。只提交这些文件,不 push。提交信息例如 `docs(<功能目录名>): 需求说明已确认`。
@@ -0,0 +1,106 @@
1
+ # <需求名称>
2
+
3
+ - 状态:草稿 / 已确认(<确认日期>)
4
+ - 档位:标准 / 快速
5
+ <!-- 执行方式选了"分阶段"或"只做研发"时,在这里加一行"- 执行方式:分阶段"或"- 执行方式:只做研发";连续执行(默认)不写 -->
6
+ - 类型:新需求 / 小改动 / 缺陷
7
+ - 版本:1
8
+ - 格式:req-kit/spec@1
9
+ - 需求提出人:<姓名或角色>
10
+ - 功能目录:`docs/features/<YYYYMMDD>-<英文短名>/`
11
+ - 对齐记录:`alignment.md`
12
+
13
+ ## 1. 背景与目标
14
+
15
+ <现在遇到了什么问题,影响了谁。两三句话。>
16
+
17
+ **目标**:<做成之后,什么会变好。>
18
+
19
+ **怎么衡量做成了**:<可以观察或统计的结果。>
20
+
21
+ ## 2. 用户与使用场景
22
+
23
+ | 角色 | 是谁 | 在什么情况下会用到 |
24
+ | --- | --- | --- |
25
+ | <角色名> | <一句话描述> | <典型场景> |
26
+
27
+ ## 3. 范围
28
+
29
+ **本次要做**
30
+ - <条目>
31
+
32
+ **本次不做**(已和需求方确认)
33
+ - <条目>:<不做的原因,或以后再考虑>
34
+
35
+ ## 4. 主流程
36
+
37
+ <按顺序描述用户从开始到结束会经历的每一步,以及每一步之后系统的表现。可以提到页面、接口、字段,不写代码实现。>
38
+
39
+ 1. <步骤>
40
+ 2. <步骤>
41
+
42
+ ## 5. 功能需求与验收标准
43
+
44
+ 每条需求按下面的格式写。优先级:必须有 / 应该有 / 可以以后再说。验收标准的写法见 `acceptance-criteria`:前置条件、操作、预期结果,简单的可以写成一句话。
45
+
46
+ ### FR-1 <需求标题>(优先级:必须有)
47
+
48
+ <用一两句话说明用户需要什么,以及为什么。>
49
+
50
+ 验收标准:
51
+
52
+ - **AC-1.1** <标题>
53
+ - 前置条件:<数据、账号、环境>
54
+ - 操作:<做了什么>
55
+ - 预期结果:<应该看到什么>
56
+ - **AC-1.2** 在<异常或边界情况>下,当<做了什么>,应该<看到什么结果>。
57
+
58
+ ### FR-2 <需求标题>(优先级:…)
59
+
60
+ …
61
+
62
+ ## 6. 业务规则
63
+
64
+ | 编号 | 规则 | 例子 |
65
+ | --- | --- | --- |
66
+ | BR-1 | <计算方式、状态变化条件、限制条件等> | <一个具体的例子> |
67
+
68
+ ## 7. 权限与数据
69
+
70
+ - **谁能看 / 谁能改**:<按角色说明>
71
+ - **涉及的业务信息**:<有哪些信息,哪些是必填,哪些敏感>
72
+ - **已有数据和进行中的业务**:<上线时怎么处理>
73
+
74
+ ## 8. 测试与验证
75
+
76
+ - **测试数据 / 账号**:<访谈中定下的>
77
+ - **验证环境**:<本地 / 测试环境 / 其他,以及需要的准备>
78
+ - **需求方会怎么验收**:<亲自试用的步骤,或者执行的命令>
79
+
80
+ ## 9. 其他要求
81
+
82
+ <只写谈到过的。例如:多久之内要有反应、同时多少人使用、需要保留多长时间的记录、哪些设备上要能用。每一条都给出可以检查的标准。>
83
+
84
+ ## 10. 假设
85
+
86
+ 没有得到需求方明确回答、由 AI 按推荐方案定下的事项。需求方请过目。
87
+
88
+ | 编号 | 假设内容 | 依据 | 如果假设不成立会影响什么 |
89
+ | --- | --- | --- | --- |
90
+ | A-1 | | | |
91
+
92
+ ## 11. 技术假设(给方案设计阶段参考)
93
+
94
+ 访谈中没有问需求方、留给技术方案决定的事项,以及从现有代码中观察到的相关情况。这里的内容不是需求,方案设计时可以调整。
95
+
96
+ - <条目>
97
+
98
+ ## 12. 待确认问题
99
+
100
+ <定稿时这一节应该为空。>
101
+
102
+ ## 13. 术语
103
+
104
+ | 术语 | 含义 |
105
+ | --- | --- |
106
+ | <需求方使用的词> | <在本需求中的确切意思。与仓库的 `GLOSSARY.md` 保持一致> |