最近我身边的人聊 AI 编程,基本都绕不开一个现象:模型续航越来越长,能力看起来什么都会一点,但产出的代码却越来越难“收住”。你让它补个接口,它顺手把整个模块的命名风格统一了;你让它修一个超时问题,它自作主张把日志框架换掉。OpenSpec 这个名字在工作中被频繁提起,背后其实就一句话:AI 写代码,先立规矩再动手。
这里说的“规矩”,不是团队 Wiki 里那种泛泛的开发规范,而是把需求边界、验收标准、文件操作范围,写成 Agent 能读取、能校验的规矩文件。我把它引入日常项目之后,最直观的感受是 Code Review 的压力小了很多。这篇不打算复读官方文档,而是想把我踩过的坑、跑通的路子,以及它到底解决什么问题讲清楚。如果你也被 AI 的“自由发挥”折腾过,大概率用得上。
1. 模型越强,越要先把“边界”说清楚
1.1 一次把“改提示文案”做成“改业务策略”的复盘
前阵子在维护一个售后系统,客户反馈登录报错信息太生硬,于是向 AI 助手提了个很常见的需求:“把所有错误提示统一成友好文案”。
结果 Agent 真的照做了。它不仅改了前端的 error code 映射,还把后端的密码锁定、风控拦截这类安全相关提示也替换成了“操作失败,请稍后重试”。表面看文案统一了,实际上把用户最需要知道的异常原因给吞了。上线后不到半天,客服那边就陆续收到“为什么账号被锁了也不告诉我”的投诉。
回看整个过程,Agent 并没有偷懒,它甚至执行得很卖力,问题在于我的需求描述太开放。我当时只给了意图,没给边界。模型能力越强,越会顺着自然语言自动补全上下文,而这种“自动补全”一旦落到业务规则上,就是一场豪赌。
OpenSpec 针对的正是这个环节。它不会直接帮你写更多业务代码,也没有改变大模型的底层能力,而是用一个外部约束层,把“你以为说了”和“AI 真的收到”之间的那条裂缝填上。
1.2 模糊描述最终会引发哪几类失控
站在只看结果的角度,AI 写代码失控通常不是某一次的偶发,而是反复出现下面几类情况:
- 范围蔓延。一句“给订单模块加个导出”能被拆成导出中心、异步任务、权限管理和前端页面,最后写出来的东西比预期大三倍。
- 越界修改。为了解决 A 模块的一个缺陷,模型会把 B 模块里它认为“不够好”的地方一起改掉,搅乱整个提交历史。
- 验收缺失。模型跑完自认为“完成了”,但由于没有预先定义什么叫“完成”,人和 AI 的判断标准完全不一致,反复来回扯皮。
- 上下文遗忘。任务越长,后面的改动越容易偏离最初的目标,尤其是 CLI 会话,聊着聊着模型就把需求缩小或放大了。
如果你也遇到过其中任何一条,说明问题不在于“换一个更强的模型”就能解决。更强的模型只会把模糊意图执行得更彻底,错误被放大而不是被修正。
1.3 所谓立规矩,是把“人话需求”翻译成“可执行契约”
过去我们写需求文档,是给产品经理或程序员看;在 OpenSpec 的语境里,这些规矩是给大模型“看”的。所以它不需要写成一篇华丽的 PRD,而是要把自然语言拆成三样东西:
- 本次改动要覆盖的范围;
- 绝对不能碰的边界;
- 改动完成后,拿什么标准来验收。
我后来把“统一错误提示”这个需求重新写成了一份规格,只加了两条硬性约束:安全类提示保持原样;只允许修改 src/error-messages.ts 一个文件。同样的模型,再跑一遍就没有越界。模型没有变,输出的质量完全不一样,差别就在于,模型在拿到任务的同时,也拿到了一套足够明确的执行契约。
需要模型API调用? 免费领10W Token,多模型网关一键接入 Claude、DeepSeek 等主流模型。
2. OpenSpec 的核心文件不是摆设:spec、tasks、change 各管一段
2.1 spec.md:把“为什么做、做什么、不做什么”钉死
很多人以为 OpenSpec 会引入一套复杂的文件格式,实际用下来,最核心的载体就是一个 Markdown 文件:spec.md。
