安装此技能
npx skills@latest add mattpocock/skills --skill=to-spec 然后在你的编码 agent 里输入 /to-spec 。
本页目录
它做什么
to-spec 把你刚刚进行完的对话变成一份**规范文档(spec)**,并把它作为一个单独的 issue 发布到你的 issue 追踪器(issue tracker)。
它不会访谈你。当你动用它时,该决定的已经决定完了。所以它综合已知的东西(来自讨论串、代码库、你的 GLOSSARY.md 和 ADR),不会开启新一轮问题。这份规范文档记录的是你已经做过的决定。它不是用来做新决定的地方。
什么时候用它
你通过输入 /to-spec 来调用它;agent 不会主动去拿它。
当一次构建大到一场 agent 会话(session)装不下、必须拆到好几场会话里时,就用它。触发条件仅此一条:
| 你在哪里 | 该运行什么 |
|---|---|
| 你还什么都没决定 | 先用 grill-with-docs |
| 已决定,而且工作装得下一个上下文窗口(context window) | implement:跳过规范文档 |
| 已决定,而且工作跨越好几场会话 | /to-spec,然后是 to-tickets |
| 一张 wayfinder 地图已经理清 | /to-spec #<map_issue> |
前提条件
to-spec 把规范文档作为 issue 发布,所以 setup-matt-pocock-skills 必须先为这个仓库配置好一个追踪器和分诊标签(triage labels)词汇。两种追踪器都行:像 GitHub 这样的真实追踪器,或者 .scratch/ 下的本地 Markdown 文件——后者不需要任何额外配置就能用。
规范文档是一份决策记录
规范文档之所以存在,是因为上下文窗口会结束。你在质询(grilling)期间定下了许多东西:解决方案的形状、你争论过的那些选择,以及你刻意拒绝的东西。所有这一切都在一场你即将清除的对话里。规范文档把它保留下来。
所以规范文档不验证任何东西,也不决定任何东西。它用你项目自己的词汇记录你所决定的内容,好让一场全新的会话能接手这项工作,而不需要你再解释一遍。如果规范文档写了一件你从未说过的事,那就是缺陷。
先谈接缝,再写正文
在写下任何东西之前,to-spec 会先勾勒出这个功能将在哪些**接缝(seams)**上被测试,并和你一起核对它们。它偏好已有的接缝而不是新的接缝,并且尽可能挑最高的那道接缝。一次改动理想的接缝数量是一。
其他技能之后会用到这些商定好的接缝。tdd 只在事先商定的接缝上工作。code-review 对照规范文档审查 diff,所以一道没人商定的接缝会作为一条审查发现冒出来。这两条连接都经过这份文档。这就是为什么你应该在这里认真对待接缝的讨论,而不要把它留到实现阶段。
常见问题
/to-prd 去哪了?
就是这个技能,在 v1.1 里改了名。「规范文档」现在是全篇统一使用的唯一叫法,旧的 to-prd slug 不再可用,所以要用新名字重新安装。旧词汇被 spec 与 tickets 这一对取代。规范文档是目的地,也是把它固定下来的那些决定。工单(tickets) 是通往那里的步骤。如果你改变方向,删掉未完成的工单,保留规范文档。
规范文档为什么会拿到 ready-for-agent 标签?我不想让 agent 照着它去实现。
这个标签的意思是「不需要进一步分诊」:这份文档完整到足以让一个 agent 据此工作。它标记的是一份输入,而不是一张工作单。但那些轮询 ready-for-agent 的离开键盘(AFK) agent 看不出这个区别。它们会试图在一次运行里构建整份规范文档,而不是拿起那些工单切片。这是关于这个技能报告得最多的问题。在它改变之前,要么在你的 AFK agent 提示词里明确排除父规范文档,要么在 /to-tickets 跑完后把标签移除。
为什么不直接从质询走到 /to-tickets,跳过规范文档?
很多时候你就该这样。规范文档只在跨多场会话的工作里才值得占那一步。它的价值在于:工单是一次性的,规范文档不是。每个工单的大小都按一个全新的上下文窗口来定,随后就被删除或关闭,而规范文档留了下来,作为记录它们背后推理的唯一地方。在一次单场会话的改动里,这什么也给不了你,你还要多付一步综合的代价,而模型(model)在这一步里可能跑偏。从质询直接走到 /implement。
我刚完成一张 wayfinder 地图。我该喂给它什么?
给它主地图那个 issue,也就是 /to-spec #<map_issue>,而不是一个个决策工单。wayfinder 产出的是散布在一张地图上的决定,不是可交付物。to-spec 把它们收拢成一份你可以据以构建的文档。如果你把地图直接灌进 /implement,你就丢掉了这一步。
规范文档是给我审阅的,还是只给 agent 的? 主要是给 agent 的,读起来也是那样:完整、密集、满是引用。你要读接缝和范围之外那一节。在这两个地方,一个错误的决定现在发现最便宜,以后发现最贵。人们确实会抱怨要读完整篇,而且没有摘要模式。但如果规范文档让你感到意外,那是质询太浅了,而不是规范文档太长。
工单开始之后,我是把规范文档冻结,还是让 agent 重写它?
没有任何东西让它保持同步。在实践中,它是你在那一刻所知内容的快照,而实现第一次教会你新东西时,它就过时了。工作上线之后,把它当作一次性产物。你的 GLOSSARY.md 和 ADR 才是本该长久保留的文件。如果你在实现期间学到某种应当长久保留的东西,把它放进那里,而不是放进一份被改过的规范文档里。
我的工作是一次重构或一条模块边界,不是一个功能。模板合适吗? 不太合适,这是一个已知局限。模板严重依赖用户故事,而用户故事不适合架构层面的工作。最后你会围绕一些实际上关于接口和不变量的决定,写出没人要求的用户故事。改用实现决策和测试决策这两节。把那些长久的架构决定通过 grill-with-docs 记成 ADR,而不是记在规范文档里。
它会去追踪器里查相关工作,或者引用它正在遵守的 ADR 吗? 两样都不会。它会读取并遵守它所触及领域的 ADR,但不会链接它们。它在写之前也不会去追踪器里搜索重叠的 issue,所以一份规范文档可能重复别人已经提交的工作,而没有任何东西提醒你。如果这个领域很热闹,先自己搜一遍追踪器。
/to-tickets 读不了我的规范文档:它总是被截断。
追踪器里的一个 issue 可能无法完整返回一份非常大的规范文档,而且没有本地副本可以替代。要解决这个问题,不要在 /to-spec 和 /to-tickets 之间清除(clearing)或压缩(compaction)。在同一场窗口里运行它们,/to-tickets 就永远不必再取一次规范文档。
它生效的标志
- 它开始写,而不是问你新一轮问题。
- 它在写之前先把接缝给你看,并且尽可能少提。
- 它用你项目自己的名词,而不是泛泛的产品管理套话。
- 你记得其中每一个决定都是你做过的。它没有为了让某一节填满而编造任何东西。
- 范围之外那一节列的是真实的东西。你拒绝的那些,通常是页面上最有用的几行。
它在体系中的位置
to-spec 是主构建链上的一步,但只在它的跨多场会话那条分支上:
grill-with-docs → to-spec → to-tickets → implement → code-review → retro
在上游,grill-with-docs 做出那些这个技能只负责记录的决定,而一张完成的 wayfinder 地图会在这里接入链条。在下游,to-tickets 把规范文档切成曳光弹(tracer bullet)式的工单,交给 implement 去构建。当你不确定哪个技能或哪条流程合适时,ask-matt 会为你路由。