关于 write-pr-description
用于撰写 Pull Request 正文的技能,补充 diff 未体现的动机、决策、影响和审查重点,适合准备 PR 描述的贡献者。它强调核实事实并遵循仓库模板。
主要功能
- 01收集并核实变更背景
- 02遵循仓库 PR 模板
- 03说明动机与行为变化
- 04如实报告验证情况
- 05提供针对性审查指引
- 06删去冗余表述
适用场景
- 01根据分支 diff 起草 PR 正文
- 02描述他人提交的变更
- 03按仓库模板调整描述
安装
复制下面的命令,在终端中运行。
npx skills add https:/ / github.com/ warpdotdev/ common-skills --skill write-pr-description安装后在 Claude Code 中输入/write-pr-description确认已加载。
包含的文件
除 SKILL.md 外,安装时一起下载的参考资料和脚本。
evals/evals.jsonreferences/plain-language.mdreview-guide.md详细介绍
编写 PR 描述
拉取请求描述只有一个目的:告诉审阅者差异本身无法说明的内容。
差异已经说明了哪些内容发生了变化。描述则要说明为什么要改、会影响什么、过程中做出了哪些决定,以及作者希望审阅者重点关注哪里。以下内容都由此而来。如果这里的某条规则与特定审阅者的需求冲突,请优先满足审阅者的需求。
create-pr 负责打开 PR 的具体操作。本技能负责 PR 正文的内容。
1. 起草前先收集事实
通常是你完成了这项工作,因此已经了解大部分情况。如果你要描述一个并非由你编写的分支,或刚接手一个 PR,就从这里开始。
# From a checkout of the branch
git --no-pager log <base>..HEAD # commit bodies first, they carry the why
git --no-pager diff <base>...HEAD --stat
# From a PR number, with no local branch
gh pr view <n> --repo <owner/repo> --json title,commits,files,baseRefName
gh pr diff <n> --repo <owner/repo>
先读提交说明,再看差异。提交说明通常是动机最丰富的来源。然后核实其中的说法:比如提交消息声称“与此文件中的现有模式一致”,这是对代码的断言,而且经常是错的。未经核实的说法不要转述。
通过查看来核实,而不是靠推理。值得进行的检查通常既简单又有针对性:
- 查看此次更改删除了什么。当更改是为了解决某个问题时,缺陷通常能从被删除的代码中看出来。
- 直接向系统查询某项内容的含义,而不是自行推断:用
gcloud iam roles describe查看角色的权限集,用提供方或 API 架构查看资源的字段,用解析器确认标记的作用。 - 在各个环境文件中搜索某个标志,再声称它是启用还是禁用。
- 打开注释或提交消息所指向的文件,确认其内容确实符合所述。
这类检查通常能帮你写出描述中最好的一句话。
收集差异无法告诉审阅者的信息:
- 动机。如果没有这项更改,什么会出问题、造成什么成本,或者哪些事情仍然无法实现。
- 关联的问题、规范或设计文档,以及分支中提交的任何规范文件。
- 存在切实替代方案的决策,以及替代方案未被采用的原因。
- 影响范围:除了直接改动的文件之外,这项更改还可能造成什么问题。
- 你运行了哪些验证,以及验证结果。
- 任何你不确定的地方。
2. 遵循仓库的模板
检查仓库是否有 PR 模板。如果有多个模板,选择与此次更改相匹配的模板。每个仓库的模板各不相同,因此每次都要检查,不要沿用上次 PR 的格式。
模板自身的说明优先于本指南。 如果模板写着“若此部分不适用,请删除”,这说明了该仓库的审查者希望你怎么做。请遵循模板。以下指导适用于模板未作说明的情况。
- 保留标题及其措辞和顺序。审查者和工具都会扫描这些内容。
- 用自己的话在每个标题下回答相应部分。不要照搬模板中的问题、说明性链接或示例。有四个门槛部分的模板,如果每部分都只回答一个“否”,否则可能要花两百个词。
- 如果某部分不适用,请用能体现你考虑过该部分的短语说明(例如“没有新增表”),而不是删除该部分或留空。
- 仅当陈述属实时才勾选方框。否则,保持未勾选,并在同一行简短说明原因。不要删除方框,不要勾选后附加保留条件,也不要把方框中的文字原样复述给读者。
- 保留机器读取的内容:变更日志标记、制品或媒体标记、问题关联键。检查标记在模板指定的位置是否有效。有些模板会把标记放在 HTML 注释中,而解析器会移除注释,这意味着标记即使保留在原处也会被静默忽略。请对照解析器或已合并的 PR 确认。
- 回答完说明性 HTML 注释后,可以将其删除。
如果没有模板,请使用以下格式,这与模板会要求的格式相同:
- 使用步骤 3 中的开篇段落,不加标题。该段同时说明了做什么和为什么,因此无需单独设置
Why部分。 - 如果步骤 4 要求提供审查指南,则添加
## Review guide。 ## What changed## Validation
对于小改动,这种格式可以精简。只有一行内容的标题也会带来步骤 4 所提醒的繁文缛节,因此删去只会包含一行内容的部分,让开篇段落承载相关信息。
3. 撰写正文
开篇用一到三句话说明此次更改做了什么以及原因。只读第一段的审查者也应该能判断自己是否适合审查。
如果仓库有模板,这段内容应放在模板的第一个内容部分中,不管该部分叫什么。不要在模板的第一个标题之前添加引言,也不要在模板内重复这段内容。
然后说明具体内容:
- 仅在代码中不明显时解释实现机制。新增抽象、非局部不变量或不寻常的控制流都需要一段说明。字段重命名则不需要。
- 明确说明行为变化,包括主要更改带来的副作用。这些变化可能会影响他人。对于权限变更,要说明具体方向:现在允许哪些以前不允许的操作,以及现在拒绝哪些以前允许的操作。
- 记录决策及被否决的替代方案。这是大多数描述中最有价值的内容,无法从差异中还原。如果不存在真正的替代方案,就直接说明这一决策。不要为了填充内容而凭空编造替代方案。
- 用户可见的更改应附上视觉证据:截图;如果是修改,则提供修改前后的对比。只引用实际存在的截图。
- 只链接一次相关问题、规范或讨论。如果没有,只有在仓库通过模板部分或贡献指南要求提供时才说明。对于不使用问题跟踪的仓库,声称“没有关联问题”只是为了满足检查,而非提供有用信息。绝不要编造一个看似合理的问题 ID 来填补空缺;错误链接的代价比没有链接更大。
验证
你通常运行过相关工作,因此请报告运行的命令及其结果。
如果没有运行,或只运行了部分内容,请如实说明。以下情况可能同时适用:你可能亲自验证了某项事实,同时仍在等待 CI 完成其余检查。
- 没有运行任何内容。 明确说明这一点,并列出审核者或 CI 应运行的命令。
- 由 CI 生成结果,因为检查需要你不应使用的凭据或环境。列出任务,并说明你预期它会显示什么,同时明确标记为预期而非观察结果。“预期只有一次销毁和一次创建,别无其他”能让审核者有依据核对运行结果,比保持沉默更有用。措辞必须确保不会被误读为你看到的输出。
- 分支添加了测试,但没有记录运行结果。 说明测试已添加但尚未运行,以免有人把测试列表当作测试通过的证据。
- 你无法运行检查,因为缺少设备、凭据或环境。说明这一点,并将其列为请审核者执行的检查。这不适用于你主动跳过的检查;如果你本可以运行,就应该运行。
- 结果由其他人记录,例如在较早的提交中记录了验证结果。注明来源,或省略不提。绝不要把它重新表述为你自己的观察结果。
无论适用哪些情况,每种情况都只说明一次。在三个部分重复写“未运行”,看起来像是在推诿,也会掩盖应该改为运行哪项检查。
绝不要把意图写成结果。
文案
以 ASD-STE100 为基准:使用主动语态,每句话只讲一个主题,句子控制在约 25 个词以内,使用简单时态,并在全文中为同一概念使用同一个术语。代码标识符、命令行和已确立的代码库术语属于技术名称;保持原样。规则及例外情况请参阅 references/plain-language.md。
4. 必要时添加审核者指南
当阅读顺序不明显、你希望审核者特别关注某处,或更改可能影响远超所涉及文件的内容时,请添加审核指南。如果有经验的审核者无需提示也知道该看哪里,则省略。
将指南放在靠前位置,紧接摘要之后。审核者不应为了找到从何处开始而滚过合规检查清单。如果模板没有提供标题,## Review guide 是一个合理的默认标题。
对于小型 PR,指南只需一两句话,不要单独设为一个章节。将其融入开头,不要另起标题。两段内容单独设标题只是形式主义;为六个文件指定阅读顺序也是如此。
审核指南可以包含以下部分或全部内容:
- 建议的阅读顺序,适用于阅读顺序确实重要的大型 PR。
- 关注重点:你不确定的地方、与安全相关的部分、存在有意义替代方案的决策,以及确实存在歧义的不可逆决策。
面向有经验的工程师撰写。指出代码和未决问题;绝不要解释如何审核代码。请参阅 references/review-guide.md,其中开头提供了简短说明,介绍需要查看哪些章节。
5. 精简
草稿往往很长,多出来的内容几乎从来不在思考过程里,而是堆积在那些看似必不可少的部分:检查清单的回答、测试项目清单、以及对已经说过内容的再次陈述。这些部分也最容易删除,因此这一步成本低,值得每次都做。
开始精简前,先为全文设定大致的篇幅参考:
- 仅涉及测试、配置或机械性改动,且不改变行为:一小段。
- 有实际风险面的微小改动:几百字,其中几乎全部用于说明风险,而非差异。
- 范围明确的修复或功能:四五百字。
- 有使用方的新机制:不超过一千字。
- 非常庞大或基础性的改动:约一千字,多出的篇幅主要用于说明阅读顺序和重点关注领域。
这些只是参考,不是限制。超过其中一项,就仔细检查下面的清单;但绝不意味着要删掉某项决策。
然后逐段检查,并说明每段能帮助审核者做出什么决策。如果说不出来,就删掉。通常会发现:
- 差异一眼就能看出的内容。“哈希滚动逻辑已通用化”“字段已重命名”、每个改动行对应一条要点、重述锁文件内容。例外是那些看起来像无意之举的内容,例如名称与其绑定的对象不一致。审核者看得见,却无法判断它是错误的,因此要保留。
- 改写本次差异中新增注释的内容。审核者就在差异中阅读这些注释,只需滚动一下即可看到。
- 新增测试的清单。指出哪些内容未覆盖,并大致说明改动有多少经过了测试。列出测试函数名称会显得凑字数,尤其是没有附上测试结果时。
- 对标准工具行为的解释。例如 Terraform 如何替换重命名的资源、测试宏如何轮询、React effect 何时触发、库如何生成子进程。解释这次改动,而不是审核者所用的工具。
- 对同一事实的第二次陈述。数一数:“没有关联的问题”和“没有运行任何内容”这两件事,各自只应在一处提及。值得重复说明的事实,通常是第一次没说清楚。
- 唯一作用是指向描述中其他部分的句子。同一页面中的交叉引用意味着内容放错了位置。
- 关于描述本身的句子。“由于这次改动影响范围很广,因此附上了审核指南。”直接写出指南;不要解释为什么要写。
- 提交信息尾注。
Co-Authored-By应写在提交中,而不是 PR 正文里。
即使大幅精简,也要保留:动机、行为变化、所做决策及被否决的替代方案、未解决的问题,以及影响范围。这些正是撰写描述的原因。必须删减时,先删机制细节,再删决策。
6. 自检
- 第一段是否能让审核者判断这个 PR 是否与自己有关?
- 每项测试说明是否都描述了实际运行的内容,或者明确说明未运行?
- 是否核实了从提交信息沿用的每一项事实?
- 精简时是否删掉了某项决策、被否决的替代方案或未解决的问题?压缩内容时,这些最容易被删掉,却也是最不该丢失的内容。把它们补回来。
- 描述是否符合当前分支的实际状态,而不是你一路走来的过程?
- 如果有审核者指南,是否放在靠前的位置?
反模式
讲述分支自身的历史。 这是最常见的问题。诸如“此 PR 最初包含单元测试,后来根据审查意见将其移除”或“上文的描述夸大了这一点,现已更正”这样的句子,描述的是审查者正在查看的差异中并不存在的变化。审查者看到的是相对于基准的一种状态。描述这种状态即可。
请注意,这条规则并不意味着不能说明原因:通常原因仍然重要,只需去掉变化过程。“移除了测试,因为它们只是在重复断言匹配分支”可以改为“这里没有单元测试,因为在这一层测试只会重复断言匹配分支”。
无论分支有多长,这条规则都适用。即使分支有 30 次提交,审查者看到的仍是相对于基准的一种状态。
复述差异。 按文件逐一罗列,是写出一大段却不包含任何信息的常见方式。
未经核实的说法,不论涉及什么。 夸大的测试声明是常见情况(“经过全面测试”“没有回归问题”),但对实现机制信心十足却判断错误,危害更大,因为审查者不太可能去核实。在断言某个角色允许什么、某个标志控制什么,或某个函数保证什么之前,请先核实。
给自己的工作打分。 “全面”“稳健”“整洁”“恰当”。这些填充词会损害可信度。
教训审查者。 “请检查边界情况,并确保错误处理正确。”称职的审查者本来就会这么做,而且这会挤占只有你才能提供的具体提示。
保留过时的描述。 重新修改或强制推送后,请重写正文,描述当前分支。不要在末尾附加修订日志。