文章

面向 AI 编程的 Markdown PRD 模板

产品需求文档(PRD,product requirements document)是在把工作拆成任务之前,陈述问题和范围的散文。功能规格是 SpecScore 为一项产品能力准备的文件:它做什么、为什么存在、如何表现。Markdown 是该文件的纯文本格式。规范驱动开发(SDD,spec-driven development)是先写规格、再写代码,并把规格当作事实来源的做法。在 SpecScore 里,需求(REQ,requirement)是功能内部一条有名字的规则。验收标准(AC,acceptance criterion)是可选的抽象条件,指向其中一条或多条规则。场景是用 Given、When、Then 步骤写成的具体例子。计划是把功能拆成任务的文档。任务是一个人或一个代理能够做完的一份工作。持续集成(CI,continuous integration)是对每一项提议变更的自动检查。这项检查是一条命令行界面(CLI,command-line interface)的命令 specscore spec lint,来自 specscore/specscore-cli 里的 CLI。Easy Approach to Requirements Syntax(EARS)是一条需求可以使用的句式。Claude Code 是本站 CLI Skills 插件所针对的 AI 编程代理。这份功能规格模板就是那个功能文件,再加上指回它的计划和任务。

最近更新:2026年11月5日

这份功能规格模板是什么

PRD 常常是一个人阅读的一份散文文件。SpecScore 把同一份简述存成检查器能够检查的文件。功能规格把功能称作产品规格的原子单位:spec/features/ 下的一个目录,其中的 README.md 是这份功能做什么的唯一事实来源。计划规格把计划称作把该功能分解成任务的文档。场景在 场景规格 里,是功能的 _tests/ 目录中一份具体的 Given/When/Then 文件。验收标准规格让标准保持抽象:标准说什么必须为真,场景说怎样证明。

下面的 checkout 文件就是填好的模板。连同功能索引、一份规格 README 和 specscore.yaml,specscore spec lint 以 0 条违规接受了它。这次检查运行于 2026年11月2日,用的是 specscore 0.55.1 和 0.39.1。0.39.1 是 dogfood.yml 所安装的标签。功能文件里的 Studio 工具栏那一行,是 specscore/specscore 里功能 README 所带的那一行。功能规格的必需节表格并没有列出它。

功能 README

功能规格的必需节表格说,每份功能 README 都有标题 # Feature: {Title}、紧接标题的 **Status:** 行、Summary、Problem、Behavior 节、Acceptance Criteria 节、Open Questions 节,以及遵循声明页脚。状态值是 Draft、In Review、Approved、Implementing、Stable、Amending、Rejected 或 Deprecated 之一。只有功能带有子目录时,Contents 节才是必需的。**Source Ideas:** 是可选的。被检查的文件把它设为 —。

Open Questions 从不省略。一条都没有时,该节写 None at this time. Acceptance Criteria 也从不省略。还没有定义标准时,该节写 Not defined yet.,并且 Open Questions 必须随后包含 Acceptance criteria not yet defined for this feature. 页脚是最后一行,它的 URL 是 https://specscore.md/feature-specification。

产物 frontmatter 约定说,每个产物都在 YAML frontmatter 里带 format: 键,带状态的产物还带 status:,与正文里的 **Status:** 对齐。同一项功能说明,强制这些键的 lint 规则有一段宽限期。被检查的文件包含这两个键。本页不声称 v0.39.1 这个固定版本会拒绝省略它们的文件。

specscore spec lint 接受的功能 README(2026年11月2日)
---
format: https://specscore.md/feature-specification
status: Draft
---

# Feature: Checkout validation

> [SpecScore.**Studio**](https://specscore.studio): | [Explore](https://specscore.studio/app/github.com/example/checkout/spec/features/checkout?op=explore) | [Edit](https://specscore.studio/app/github.com/example/checkout/spec/features/checkout?op=edit) | [Ask question](https://specscore.studio/app/github.com/example/checkout/spec/features/checkout?op=ask) | [Request change](https://specscore.studio/app/github.com/example/checkout/spec/features/checkout?op=request-change) |

**Status:** Draft
**Source Ideas:** —

## Summary

The checkout form shows a validation error next to a field when the shopper submits invalid data, and it rejects an email that is not a valid address.

## Problem

A vague sentence such as "the form should handle bad input" does not say which event causes which response. Checkout needs those obligations written so a reviewer and a linter can point at them.

## Behavior

### Field validation

The checkout system checks the form when the shopper submits it.

#### REQ: show-field-error

When a shopper submits the checkout form with invalid data, the checkout system MUST show a validation error next to the invalid field.

#### REQ: reject-invalid-email

If the submitted email is not a valid address, then the checkout system MUST reject the form.

## Acceptance Criteria

### AC: invalid-submission

**Requirements:** checkout#req:show-field-error, checkout#req:reject-invalid-email

Submitting the checkout form with invalid data shows a validation error next to the invalid field, and an email that is not a valid address is rejected.

## Open Questions

None at this time.

---
*This document follows the https://specscore.md/feature-specification*
同一次检查运行的功能索引
---
format: https://specscore.md/features-index-specification
---

# Features

| Feature | Status | Description |
|---|---|---|
| [Checkout validation](checkout/README.md) | Draft | The checkout form shows a validation error next to a field when the shopper submits invalid data, and it rejects an email that is not a valid address. |

## Open Questions

None at this time.

---
*This document follows the https://specscore.md/features-index-specification*
同一次检查运行的规格 README
# Checkout specification

## Open Questions

None at this time.
同一次检查运行的 specscore.yaml
# SpecScore Repo Config Schema: https://specscore.md/repo-config

project:
  title: Checkout sample
  host: github.com
  org: example
  repo: checkout

功能的标识是它相对于 spec/features/ 的目录路径。索引链接 checkout/README.md 表示文件位于 spec/features/checkout/README.md,因此需求和标准使用的功能 id 是 checkout。索引列出每一个顶层功能。没有列出的子目录是 index-entries 的违规,在 CI 中检查规格说明了这条规则。那棵树里的规格 README 只有一节,Open Questions,写的是 None at this time. 配置文件是 CLI 向上查找的那个文件。没有 specscore.yaml 时,命令以 3 退出,并点出 specscore init。

REQ 标识、验收标准与场景

需求规格把每条规则放在 ## Behavior 内部的主题标题之下。标题是 #### REQ: {slug},冒号后面是一个空格。slug 使用小写字母、数字和连字符。标准形式的 id 是 {feature-path}#req:{slug}。在 checkout 文件里,那就是 checkout#req:show-field-error 和 checkout#req:reject-invalid-email。一条需求陈述一项义务。规格说,需求 SHOULD 使用 RFC 2119 关键词 MUST、MUST NOT、SHOULD、SHOULD NOT 和 MAY。REQ: 标题在 ## Behavior 之外无效。EARS 句子可以充当那段散文。检查器不给英语打分。这些句式在 EARS 需求语法详解与示例。

验收标准

验收标准规格说,每条标准是一个 ### AC: {slug} 标题,位于 ## Acceptance Criteria 内部,然后是一行 **Requirements:**,列出 {feature-id}#req:{slug} 的值,再然后是一句抽象的话,说明什么必须为真。标准是可选的。规格说,把两条或更多相关需求归并到一起能让意思更清楚时,就加一条。checkout 文件把两条规则都归进 checkout#ac:invalid-submission。这句话里没有 Given、When 或 Then。怎样写验收标准是写作指南。规则 ac-heading-format(ac_heading.go,CLI 标签 v0.55.1)检查标题是 ### AC: <id>,并且 id 为 kebab-case。检查规格的文章记录这条规则并不要求 **Requirements:** 那一行,也不给措辞打分。验收标准规格仍然要求那一行。

场景

场景规格把场景放在 _tests/ 里。那里不是子功能,也不进入功能索引。文件以 # Scenario: {Title} 开头,有一行指向需求或标准的 **Validates:**,以及一节 ## Steps,其关键字是大写的 GIVEN、WHEN、THEN 和 AND。每个 _tests/ 目录都必须有一份带场景索引的 README。下面的样本就是那种文件形状。它不属于 2026年11月2日的那次检查。specscore spec lint 不检查场景步骤关键字。specscore rehearse 运行场景文件。Rehearse 就是那个运行器。dogfood 工作流运行检查器,并不调用 rehearse。

按场景规格得到的场景文件形状
# Scenario: Reject an invalid email

**Validates:** [checkout#ac:invalid-email-rejected](../README.md#ac-invalid-email-rejected)

## Steps

GIVEN the shopper is on the checkout form
WHEN the shopper submits the email "not-an-email"
THEN the page shows "Enter a valid email address" beside the email field
AND the order is not placed

按顺序读这三层。需求说出规则。验收标准说出它所点名的规则必须为真的是什么。场景给出一条具体流程。只看得到 PRD 散文的代理,得自己发明这层拆分。模板里已经有了。

计划与任务

计划 README 位于 spec/plans/{plan-slug}/README.md。计划规格要求标题 # Plan: {Title},以及头部字段 Status、恰好一行来源、Date、Owner 和 Supersedes。以来源为功能的计划使用 **Source Feature:** 加上功能 slug,这里是 checkout。另外允许的来源行是 **Source:** idea:{slug} 和 **Source:** none。必需的节是 Summary、Approach、Tasks 和 Open Questions。计划内部,每条任务是一个 ### Task N: 标题,带一行 **Verifies:**,形式为 feature-slug#ac:ac-slug。规则 P-001(在 plan_rules.go)报告一条没有任何任务覆盖、也没有列在 ## Deferred AC Coverage 之下的验收标准标题。规则 P-002 报告一个对不上那些标题的 **Verifies:** 值。来源为 idea 的计划,以及带 **Source:** none 的计划,免除 P-001。

下面的计划按已公布的形状为 checkout 功能填写,包括 frontmatter 里的 format: 和 status:。它不在 2026年11月2日的那次检查里。计划触及的功能必须包含一张 ## Plans 表,列是 Plan、Status、Author 和 Approved。被检查的功能文件没有 Plans 节,因为那棵树里没有计划。

任务规格还把任务定义为计划之下自己的目录和 README.md。标题是 # Task: {Title}。必需字段是 **Status:**、**Depends on:**(没有依赖时的字面量是 none)和 **Model:**(small、medium、large 或 inherit)。包含子任务目录的目录是计划,不是任务。下面的任务文件把这些字段用于 checkout 的第一个任务。它不在 2026年11月2日的那次检查里。任务文档的页脚 URL 是 https://specscore.md/task-specification。

按计划规格的形状,为 checkout 填好的计划
---
format: https://specscore.md/plan-specification
status: Draft
---

# Plan: Show checkout validation errors

**Status:** Draft
**Source Feature:** checkout
**Date:** 2026-11-05
**Owner:** @example
**Supersedes:** —

## Summary

This plan decomposes the checkout feature into the work that shows a field error and rejects an email that is not a valid address.

## Approach

Both tasks verify the same acceptance criterion, which bundles the two requirements. Nothing is deferred, so this plan has no Deferred AC Coverage section.

## Tasks

### Task 1: Show a validation error beside the invalid field

**Verifies:** checkout#ac:invalid-submission

When the shopper submits the checkout form with invalid data, show a validation error next to the invalid field.

### Task 2: Reject an email that is not a valid address

**Verifies:** checkout#ac:invalid-submission

If the submitted email is not a valid address, reject the form.

## Open Questions

None at this time.

---
*This document follows the https://specscore.md/plan-specification*
按任务规格得到的任务文档形状
---
format: https://specscore.md/task-specification
status: queued
---

# Task: Show a validation error beside the invalid field

**Status:** queued
**Depends on:** none
**Model:** medium

## Acceptance Criteria

- Submitting the checkout form with invalid data shows a validation error next to the invalid field.

## Open Questions

None at this time.

---
*This document follows the https://specscore.md/task-specification*

功能文件回答 checkout 表单必须做什么。计划回答这项工作如何拆分,每条行内任务都写出它所验证的标准。任务文档是人或代理接手的末端。让标准的标识保持不变。checkout#ac:invalid-submission 就是功能和计划都使用的那串文字。

在 CI 中检查这份模板

specscore spec lint 对照结构约定的违规来验证规格树。一次干净的运行打印 0 violations found 并以 0 退出。发现违规的运行为每条发现打印一行,并以 1 退出。这个退出码会让 CI 作业失败。无效参数以 2 退出。缺少 specscore.yaml 时以 3 退出。dogfood.yml 把 SPECSCORE_VERSION 设为 v0.39.1 来安装 CLI,然后在 pull request 以及推向 main 的 push 上运行 specscore spec lint。工作流摘录、失败报告和规则一览在 在 CI 中用规格检查器检查规格。

格式许可证是 CC BY 4.0,位于 specscore/specscore。CLI 许可证是 Apache-2.0,位于 specscore/specscore-cli。

其他规范驱动工具公布的检查各不相同。下面的句子只用那些项目自己的页面所说的内容。工具综述把同样的页面记为 2026年10月30日读过,Spec Kit 文档首页除外,那一页印着 2026年9月28日。

OpenSpec 记录了 openspec validate,写在它的 CLI 参考 里。该命令检查 OpenSpec 的变更和规格结构,验证失败时以非零退出。它不检查 SpecScore 的 ### AC: 标题,也不检查 SpecScore 的索引。

Task Master 的 README 描述用 task-master parse-prd 把 PRD 解析成任务。它没有描述针对那份 PRD 的检查器。PRD 仍然可以是你改写成此页功能文件的输入。随后检查该功能文件的是 specscore spec lint。

GitHub Spec Kit 描述一套代理工作流,其阶段写下 Markdown 产物。那份文档首页没有描述一条在 CI 中检查 SpecScore 功能 README 的命令。那些工具的比较是 工具综述。

Claude Code 能读的规格模板

这些文件是 Markdown,所以能读取仓库的代理就能读取这份模板。Claude Code 是 CLI Skills 页面所针对的代理。该页记录了 ai-plugin-specscore,一个包住 CLI 的薄 Claude Code 插件。插件仓库是 specscore/ai-plugin-specscore。该页说,插件把 specscore spec lint、specscore feature、specscore task 和 specscore feature change-status 作为插件命令露出。该页上的安装行是 /plugin marketplace add specscore/ai-marketplace 和 /plugin install cli-skills@specscore。

同一页还记录了在 SpecScore 管理的项目里运行的 specscore agent setup <agent-name>,用于 claude、copilot、cursor、codex、antigravity.google、pi.dev 或 opencode。SpecStudio Skills 是有引导的工作流(/ideate、/specify、/plan、/implement),并且也是一个 Claude Code 插件。本页的模板就是那些命令所检查的文件。插件不代替功能 README。

常见问题

什么是 Markdown 中的 PRD 模板?

它是写成固定形状的 Markdown 文件的产品需求文档。在 SpecScore 里,这个形状是一份功能 README:标题、状态、摘要、问题、带 #### REQ: 规则的行为、验收标准,以及开放问题。本页的 checkout 文件就是 specscore spec lint 接受过的一份。

功能规格模板里,REQ 标识放在哪里?

放在 ## Behavior 内部的主题标题下,写作 #### REQ: {slug}。标识是 {feature-path}#req:{slug}。验收标准在 **Requirements:** 上列出这些标识。计划里的任务在 **Verifies:** 上列出标准标识。

验收标准和场景有什么不同?

验收标准是抽象条件。场景是 _tests/ 里一条具体的 Given/When/Then 流程。验收标准规格说,标准不得规定步骤。场景文件则会写出步骤。

检查器会给 PRD 的散文打分吗?

不会。specscore spec lint 检查的是结构:标题、必需的节、索引行,以及 P-001 和 P-002 这样的引用。它不判断产品是不是个好主意。在 CI 中用规格检查器检查规格 是对那条命令更长的说明。

Claude Code 能用这份规格模板吗?

能。模板是仓库里的 Markdown。CLI Skills 插件在 Claude Code 里露出 specscore spec lint,以及功能和任务命令。specscore agent setup claude 为那个代理写一份指示文件。插件不会另造一份模板。

计划会代替功能规格吗?

不会。功能 README 是需求和验收标准的来源。计划把该功能分解成任务,每条任务用 **Verifies:** 指回去。计划规格 和 任务规格 就是这次拆分的两份文档。

把 PRD 放进 CI 可以拒绝的文件。

发现翻译问题或有改进此页面的想法?