1. 为什么需要 OpenSpec?
日常与 AI 编码助手(例如 Cursor、Claude Code、Qoder 等)协作时,你是否也频繁遭遇以下令人困扰的痛点?
- 需求“漂移”:对话历史一长,AI 便彻底遗忘最初需求,开始自由发挥,结果越走越偏。
- 遗漏细节:口头描述的需求,AI 往往忽略边界条件、非功能性要求等关键信息,最终产出与预期相差甚远。
- 不可复现:上次效果良好的 Prompt,这次再次使用,生成的结果却完全对不上号,只能反复调试。
这些问题的根源,都在于缺乏一份清晰的“协议”。OpenSpec 正是为解决这一痛点而生:一个轻量级框架,核心原则只有四个字——规范先行。在编写任何代码之前,先让人与 AI 就“要做什么”达成一份可审查、可落地的协议,而非依赖对话记忆碰运气。
简而言之,OpenSpec 相当于为 AI 提供了一张结构化的“施工蓝图”,将模糊闲聊式的开发方式,转变为严谨的工程化流程。
2. 核心概念
目录结构与“两库分离”
OpenSpec 通过在项目中添加一个 openspec/ 根目录来管理工作流。其设计精髓在于——“真相源”与“变更提案”在物理上是完全分离的。
openspec/
├── specs/ # 【真相源】当前系统已实现的“确定性”行为
│ └── [功能模块]/
│ └── spec.md
├── changes/ # 【工作区】待实现的“提议”变更
│ ├── [变更名称]/ # 例如:add-dark-mode
│ │ ├── proposal.md # 为什么要改?改什么?
│ │ ├── design.md # 技术方案与决策
│ │ ├── tasks.md # 实施清单(Checklist)
│ │ └── specs/ # 针对真相源的“增量补丁”
│ └── archive/ # 已完成的历史归档
specs/类似主干,记录项目当前的真实全貌。现有项目接入时,可让 AI 参考 OpenSpec 规范追溯生成 specs。changes/则是分支,每个变更都是一个独立文件夹,包含该变更的所有计划、设计和增量规范。这样变更范围清晰可控,多人并行开发也不会冲突。
增量规范
增量规范是 OpenSpec 中的关键概念——它明确告诉你:与当前规范相比,究竟多了哪些改动。
3. 环境搭建与初始化
环境要求
- Node.js 20.19.0 或更高版本。
安装 CLI 工具
# 安装官方版本
npm install -g @fission-ai/openspec@latest
# 或中文优化版
npm install -g @studyzy/openspec-cn
在项目中初始化
进入项目根目录,执行初始化命令:
cd your-project
openspec init # 中文版使用 openspec-cn init
两种模式
默认快速路径(core配置文件)
/opsx:propose/opsx:explore/opsx:apply/opsx:archive
典型流程:
/opsx:propose ──► /opsx:apply ──► /opsx:archive
初始化时,CLI 会询问你使用的是哪个 AI 工具(如 Cursor、Claude Code、Qoder 等)。选择后,它会在对应目录自动生成快捷命令(Slash Commands)和 Skills,让你可以在聊天框中直接驱动整个流程。
扩展/完整工作流程(自定义选择)
通过运行 openspec config profile,可以选择更多命令:/opsx:continue、/opsx:ff、/opsx:verify、/opsx:sync、/opsx:bulk-archive、/opsx:onboard。
4. 核心工作流(三/四步法)
以官方 demo + 快捷命令为例:为现有的 Web 应用增加深色模式(Dark Mode)。
第一步:探索需求
在 AI 对话框输入 /opsx:explore:
AI 会先了解现有架构,整理出关键问题与你探讨。等所有不确定性消除后,生成最终方案,由你决定是否进入 proposal 阶段。
如果需求已经非常明确,可以跳过这一步,直接使用三步模式:
你:/opsx:propose add-dark-mode
AI:已创建 openspec/changes/add-dark-mode/
✓ proposal.md — 为什么要做这个,什么在变
✓ specs/ — 需求和场景
✓ design.md — 技术方案
✓ tasks.md — 实现清单
准备好开始实现了!
你:/opsx:apply
AI:开始实现任务...
✓ 1.1 添加主题上下文 Provider
✓ 1.2 创建切换组件
✓ 2.1 添加 CSS 变量
✓ 2.2 接入 localStorage
所有任务已完成!
你:/opsx:archive
AI:已归档至 openspec/changes/archive/2025-01-23-add-dark-mode/
Specs 已更新。可以开始下一个功能了。
第二步:创建变更
在 AI 对话框输入 /opsx:propose:
AI 会自动在 changes/ 目录下创建一个文件夹(例如 add-dark-mode),并生成以下工件(Artifact):
proposal.md:阐述动机、影响范围、验收标准 (MUST/SHOULD)。
# 提案:添加深色模式
## 意图
用户要求提供深色模式选项,以在夜间使用时减少眼睛疲劳并匹配系统偏好。
## 范围
包含:
- 设置中的主题切换
- 系统偏好检测
- 在 localStorage 中持久化偏好
不包含:
- 自定义颜色主题(未来工作)
- 每页主题覆盖
## 方法
使用 CSS 自定义属性进行主题化,配合 React context 进行状态管理。在首次加载时检测系统偏好,允许手动覆盖。
design.md:技术决策(如用 CSS 变量还是 CSS-in-JS)、风险分析。
# 设计:添加深色模式
## 技术方法
通过 React Context 管理主题状态以避免属性传递。CSS 自定义属性支持运行时切换而无需类切换。
## 架构决策
### 决策:Context 优于 Redux
使用 React Context 管理主题状态的原因:
- 简单的二元状态(浅色/深色)
- 无复杂状态转换
- 避免添加 Redux 依赖
...
## 文件变更
- `src/contexts/ThemeContext.tsx`(新建)
- `src/components/ThemeToggle.tsx`(新建)
- `src/styles/globals.css`(修改)
tasks.md:具体的编码任务清单。
# 任务
## 1. 主题基础设施
- [ ] 1.1 创建具有浅色/深色状态的 ThemeContext
- [ ] 1.2 添加 CSS 自定义属性用于颜色
- [ ] 1.3 实现 localStorage 持久化
- [ ] 1.4 添加系统偏好检测
## 2. UI 组件
- [ ] 2.1 创建 ThemeToggle 组件
- [ ] 2.2 在设置页面添加切换器
- [ ] 2.3 更新 Header 包含快速切换
## 3. 样式
- [ ] 3.1 定义深色主题调色板
- [ ] 3.2 更新组件使用 CSS 变量
- [ ] 3.3 测试可访问性的对比度比率
specs/ui/spec.md:增量规范。
# UI 变更增量规范
## 新增需求
### 需求:主题选择
系统必须(SHALL)允许用户在浅色主题和深色主题之间进行选择。
#### 场景:手动切换
- **假设** 用户在任意页面上
- **当** 用户点击主题切换按钮
- **则** 界面主题立即切换
- **并且** 用户的选择偏好会在会话间持久保存
#### 场景:跟随系统偏好
- **假设** 用户没有保存过任何主题偏好
- **当** 应用加载时
- **则** 使用操作系统偏好的配色方案
Artifact 生成完成后,你先阅读 proposal.md 和 specs/。如果发现 AI 的理解有偏差,可以直接修改 Markdown 文件,或在对话中纠正它。例如:
第三步:实施编码
提案锁定后,输入实施命令:
此时 AI 的行为会被严格“约束”——它不再自由发挥,而是严格依据 tasks.md 和 spec.md 中的场景来编写代码。每完成一项任务,它通常会在 tasks.md 中打勾 [x]。
第四步:归档与沉淀
代码合并、功能上线后,执行归档:
AI 会把 changes/add-dark-mode/specs/ 中的增量修改合并回 specs/theme/spec.md 主目录,同时将 add-dark-mode 文件夹移入 archive。自此,深色模式成为项目的“既定事实”,未来的变更都会基于更新后的规范。
更多工作流示例参考
5. 核心命令速查表
上面演示的都是最基本的用法,许多命令还支持参数,未一一列出。完整命令可参考(汉化版)。
AI 对话斜杠命令 (Slash Commands)
| 命令 | 阶段 | 作用 |
|---|---|---|
/opsx:explore | 探索 | 非正式讨论需求,不生成文件,仅对话 |
/opsx:propose | 规划 | 创建变更文件夹,生成提案和设计草稿 |
/opsx:apply | 实施 | 按照任务清单和规范编写代码 |
/opsx:archive | 归档 | 完成变更,更新主规范,移入存档 |
终端 CLI 命令
| 命令 | 作用 |
|---|---|
openspec list | 查看当前活跃的变更列表 |
openspec show | 查看变更详情 |
openspec validate | 校验规范格式是否正确 |
openspec archive | 非交互式归档(CI/CD 中用) |
扩展自定义
| 命令 | 作用 |
|---|---|
/opsx:new | 启动新的变更,功能同/opsx:propose |
/opsx:continue | 显示有哪些可以继续处理的未完成的变更,重复使用此方法可以逐步构建更改。 |
/opsx:ff | 一次性生成所有规划工件(Artifact),一般在/opsx:new之后执行 |
/opsx:verify | 验证实现是否与工件一致 |
/opsx:sync | 将增量规范同步到主规范 |
/opsx:bulk-archive | 归档多个已完成的更改 |
/opsx:onboard | 引导式完整变更流程教学 |
6. 项目配置
openspec/config.yaml 项目配置允许你设置默认值,并将项目特定的上下文注入到所有工件中。
创建配置
配置可以在 openspec init 过程中创建,也可以手动创建:
# openspec/config.yaml
schema: spec-driven
context: |
Tech stack: TypeScript, React, Node.js
API conventions: RESTful, JSON responses
Testing: Vitest for unit tests, Playwright for e2e
Style: ESLint with Prettier, strict TypeScript
rules:
proposal:
- Include rollback plan
- Identify affected teams
specs:
- Use Given/When/Then format for scenarios
design:
- Include sequence diagrams for complex flows
配置字段
| 场地 | 类型 | 描述 |
|---|---|---|
schema | 字符串 | 新变更的默认架构(例如,spec-driven) |
context | 字符串 | 项目上下文,会注入到所有工件指令中 |
rules | 对象 | 每个工件的规则,以工件 ID 为键 |
7. OpenSpec vs 其他工具
| 特性 | OpenSpec | spec-kit | 普通 Prompt 编程 |
|---|---|---|---|
| 核心优势 | 棕地项目优化、变更可追溯 | 绿地项目 (0→1) 强 | 快速原型 |
| 变更管理 | 独立文件夹,增量补丁清晰 | 结构较弱 | 依赖聊天记忆 |
| 协作性 | 规范即文档,可脱离对话审查 | 同上 | 无法审查,不可复现 |
OpenSpec 特别适合在现有复杂项目上进行迭代——尤其是当修改会波及多个模块时,它的“增量补丁”机制能有效控制范围蔓延。
8. 总结
OpenSpec 并非取代你的 IDE 或 Git,而是作为 AI 编码助手的“协议层”存在。它通过将模糊的意图固化为清晰的 Markdown 规范,解决了 AI 编程最大的痛点——不确定性。
最佳实践建议:
- 从小处着手:不要一开始就想全量改造。下次修 Bug 或加小功能时,试着用 OpenSpec 流程走一遍,感受其效果。
- 规范即代码:把
openspec/文件夹提交到 Git 仓库,它会成为团队的知识库和审计日志,长期受益。
