最近看到一篇很长的文章,主题是 Harness 最佳实践:在 Java Spring Boot 项目中落地 OpenSpec + Claude Code。看完之后,我觉得它最有价值的地方,不是又介绍了一个“新概念”,而是把一件很多团队已经隐约意识到、但还没系统化表达的事情讲清楚了:
AI 真正要进入生产研发流程,重点从来不是“它能不能多写点代码”,而是“它能不能在边界内、按流程、可审计地工作”。
这也是我对 Harness 这个词最直白的理解:不是让 AI 更自由,而是让 AI 在工程规则里稳定工作。
文章到底在讲什么
如果只用一句话概括,原文想解决的问题是:
怎么把 AI 从一个“偶尔帮忙写代码的工具”,变成一套真正能进入团队研发流程的工程能力。
作者拿 Java Spring Boot 项目做例子,但里面很多原则并不只适用于 Java。只要你的项目已经有一定历史包袱、业务约定复杂、上线风险不低,这套思路其实都值得参考。
文章一开始就点到了一个很现实的问题:
- AI 最大的风险,不是写不出来
- 而是它在你没有明确约束的时候,去碰了高风险区域
- 比如 SQL、配置、脚本、部署、隐性业务约定这些地方
很多“AI 翻车”不是模型不够聪明,而是团队没有把规则、流程和边界准备好。
这套思路的核心,其实只有四件事
我把原文压缩之后,觉得真正值得记住的是下面四条。
1. 用 OpenSpec 管住变更生命周期
作者推荐的主流程是:
/opsx:propose -> /opsx:apply -> /opsx:verify -> /opsx:archive
这个流程的意义,不只是多了几个命令,而是把一次需求变更拆成了完整生命周期:
propose:先拆需求,形成 proposal、design、tasksapply:按确认后的方案实施,不边做边扩需求verify:检查实现是否和变更工件一致archive:归档,清理上下文,避免 change 污染
这背后的核心思想我很认同:
先把“要改什么”说清楚,再让 AI 去“怎么改”。
很多时候,AI 不是实现错了,而是从一开始就理解错了边界。
2. AGENTS.md 只做导航,不做百科全书
这是原文里我很赞同的一点。
很多团队会下意识把所有规则都往 AGENTS.md 里堆,最后变成一个又长又乱的大杂烩。AI 每次进仓库先看一坨规则,但真正项目知识又埋在里面,效果其实并不好。
更合理的分层应该是:
AGENTS.md:告诉 AI 先看什么、按什么流程做docs/:承载真正的项目知识、业务规则、历史坑点、隐性约定
也就是说,AGENTS.md 更像入口地图,docs/ 才是知识库。
这个思路特别适合老项目。因为老项目最大的问题,往往不是代码难,而是“知识分布混乱”。
3. 真正的硬约束不能只靠提示词,要靠 permissions 和 hooks
这一点其实非常工程化。
写在文档里的规则,本质上都是软约束。AI 可能遵守,也可能在复杂上下文里漏掉。而真正能把事故概率压下来的,是硬护栏。
比如下面这些目录,本来就应该默认高风险:
application*.ymlbootstrap*.ymldb/sql/deploy/infra/secrets/
对于这些路径,原文的建议很明确:
- 权限层先 deny
- hook 再做一次路径校验
同理,命令执行也要分层:
允许的可以是:
mvn testmvn -DskipTests compilegit diffgit status
默认禁止的应该是:
git pushkubectlterraformhelmrm -rf
这套设计本质上是在回答一个问题:
当模型判断失误时,谁来兜底?
答案不应该是“希望它别出错”,而应该是“系统本身拦得住”。
4. 把评审能力拆开,不要混成一个动作
原文非常强调:实现、验证、评审、架构检查、SQL 风险检查,这些不能混为一谈。
比如:
/opsx:verify只负责检查实现是否和 OpenSpec 工件一致/prepare-review负责整理改动摘要,方便人工 review/spring-architecture-review检查 Spring 分层是否被破坏/sql-risk-review检查 SQL / Mapper / 批量更新风险reviewer子代理做只读视角的独立审计
这个设计的好处很明显:
- 每种检查目标单一
- 不容易相互覆盖又相互遗漏
- 出问题时更容易定位,到底是 proposal 错了,还是实现偏了,还是架构/SQL 风险没控住
这比“让 AI 最后自己 review 一遍”靠谱得多。
我最认同的一点:隐性约定必须显性化
如果让我从整篇文章里只挑一个最值钱的点,我会选这个。
真实项目里最坑人的,往往不是写在文档里的规则,而是那些:
- 大家都知道
- 但没人明确写下来
- 一旦改错,代码能跑,联调却出问题
比如:
- 某个字段的
null和0历史语义并不一样 - 某个接口里某个字段前端就是依赖它回显
- 某个状态流转不能只看表面枚举值
这种东西,人靠口口相传还能勉强维持;一旦交给 AI,如果没有文档,它几乎不可能稳定猜对。
所以作者建议把这些内容单独沉淀到类似:
docs/architecture/implicit-contracts.md
我觉得这不是“文档工作”,这是工程降风险工作。
AI 时代,很多团队要补的不是 prompt,而是项目知识本身。
这套方式适合什么项目
文章里给的判断也比较务实。
它最适合的不是小 demo,也不是一次性脚本,而是这类项目:
- 有一定历史包袱的业务系统
- 有较多口头约定或隐性契约
- 希望把 AI 编码从“个人技巧”变成“团队流程能力”
如果只是一个纯实验项目、从 0 到 1 的小仓库,没必要一下子把约束拉满。因为约束太重,本身也会降低效率。
这一点我也认同:
Harness 不是越重越好,而是要和项目复杂度、风险等级匹配。
放到 Spring Boot 项目里,最值得优先加护栏的地方
原文提了几个点,我觉得基本都踩在真实痛点上:
Controller 里写业务逻辑
这是很多老项目最常见的脏点。AI 一旦顺着已有坏味道继续写,只会越堆越乱。
直接改 SQL、配置、数据库脚本
这种改动本地跑通不代表线上安全。很多事故都不是复杂逻辑错了,而是这些底层东西被轻率改动。
Service 越写越胖
AI 连续补代码的时候,很容易把各种职责都堆到一个 Service 里。短期看省事,长期会让系统越来越难维护。
测试只覆盖 happy path
这是传统开发会犯的毛病,AI 也一样会犯。尤其是它往往倾向于补一个“能过的测试”,而不是补真正有约束力的测试。
批量更新没有 where 限制
这不是普通 bug,这基本就是事故预备动作。数据库规范和 SQL 风险审查必须把它当成显式检查项。
我自己的理解:Harness 不是新发明,而是旧工程经验的新组织方式
看完这篇文章,我最大的感受其实是:
Harness 并不是什么横空出世的新发明。
以前没有 AI 的时候,我们也一直在做类似的事:
- 定规则
- 做权限控制
- 分层审查
- 跑自动检查
- 给高风险动作加护栏
- 把知识沉淀到文档
只是以前这些事情是分散的,没有一个统一的名字。现在因为 AI coding 普及,大家突然发现:这些工程经验必须重新被系统化,必须真正放到流程前面。
所以 Harness 对我来说,不是一个“追新词”的事情,而是一个提醒:
当工具越来越强时,工程边界反而要更清楚。
AI 不是不能放进生产流程,而是不能裸奔进生产流程。
如果让我给团队一个最小落地建议
不一定一上来就把整套体系铺满。我会更建议按下面这个顺序慢慢上:
第一阶段:先把最小闭环跑通
先有这些:
- OpenSpec change 生命周期
AGENTS.mddocs/知识分层- 隐性约定文档
- 一个只读 reviewer
先解决“能不能把一次需求改动完整走完”。
第二阶段:补硬护栏
再加:
- permissions
- 写入保护 hook
- change 上下文检查
- 自动编译 / 测试 / 打包校验
把高风险动作拦起来。
第三阶段:再做团队专用能力沉淀
比如:
- Spring 架构审查 skill
- SQL 风险审查 skill
- PR 摘要整理 skill
- 子代理 reviewer
到这个阶段,AI 才开始从“会写代码的助手”变成“能参与团队流程的一环”。
最后
这篇文章最值得看的地方,不是它给出了某个唯一正确的目录结构,而是它讲清楚了一件事:
AI coding 真正进入生产,不靠模型自己突然变得足够聪明,而靠团队把流程、知识、权限、审查和约束搭起来。
工具能力越强,越不能只靠“感觉它应该知道”。
把需求工件化,把隐性约定写下来,把危险路径锁住,把审查动作拆开,把 change 生命周期走完整——这些听起来不性感,但真正能决定 AI 最后是在帮你提效,还是在帮你制造隐患。
如果只记一句话,我会记这句:
AI 不是要“放开跑”,而是要“在可控的路上稳定跑”。
参考原文:
[万字长文预警] Harness 最佳实践:在 Java Spring Boot 项目中落地 OpenSpec + Claude Code
https://mp.weixin.qq.com/s/3qKvWajntkYLArH4ZShAhg