Agent不好使真不是模型的锅——Harness Engineering四个支柱我是这样理解的
最近用AI Agent写代码,发现一个很有意思的现象:有时候它写出来的代码质量很高,几乎不用改;有时候一塌糊涂,来回改比自己写还慢。同一套工具,同一个模型,为什么差别这么大?
琢磨了一阵,我发现问题不在模型,在环境——Agent在什么条件下干活,比Agent本身有多强重要得多。换个更强的模型是本能反应,但往往不是解决问题的那一下。真正拉开差距的,是你给Agent搭了一个什么样的工作环境——系统提示词怎么写的、工具接口怎么设计的、文件怎么组织的、跑完代码有没有自动检查。这些东西模型一个参数没动,但效果可以天差地别。
后来我知道了,这套"给Agent搭环境"的思路有个名字,叫Harness Engineering。Terraform和Vagrant的作者Mitchell Hashimoto在2026年2月首次提出这个概念,六天后OpenAI发官方实验报告直接引用了。这篇把我的理解整理成文。
不是模型不行,是你没给它搭好环境
一个公式就够了:Agent = Model + Harness。模型是引擎,Harness是引擎外面的一切——系统提示词、工具接口、文件系统、沙箱、编排逻辑、钩子、反馈回路、约束机制。你不是模型,那你做的所有事情大概率都是Harness的一部分。
换个方式理解:模型是一个新入职的员工,Harness是公司给他搭的工作环境和管理制度。同样是能力不错的人,去一家没有项目文档、没有编码规范、没有代码审查、没有自动化测试的公司,时间一长也会写出混乱的代码。去另一家文档齐全、代码规范有自动检查兜底、必须过审查、测试覆盖到位的公司,同样的能力,产出质量完全不同。人没变,环境变了。
Harness Engineering的核心思路:每当Agent犯了一个错,你不应该想"换个更强的模型",而应该想"怎么把环境修好,让它以后不会再犯同类错误"。Agent的每一次失败,都是环境设计不完善的信号。
你可能听过Prompt Engineering和Context Engineering,它们和Harness是什么关系?一层套一层。Prompt解决"怎么跟AI说话",Context解决"该给AI看什么信息",Harness解决"AI在什么条件下运行"。简单任务Prompt就够了,需要外部知识时Context更重要,到了要长时间稳定执行任务的场景,Harness就变成了主要矛盾。Context Engineering其实是Harness Engineering的一个子集。
四个支柱:上下文、约束、反馈、清理
Harness Engineering有四个核心支柱:上下文工程、架构约束、反馈循环、熵管理。分开说,后面再用一个具体的例子把四个串起来。
塞得多不如给得准-上下文工程
很多人以为上下文工程就是"给Agent塞更多信息"。恰恰相反,核心是在合适的时机给合适的信息。
举个我自己的例子。我刚开始用Claude Code的时候,恨不得把项目里所有文件都塞进上下文——架构文档、编码规范、API定义、数据库schema,一股脑全丢进去。结果Agent反而更蠢了,输出的东西开始不聚焦,有时候还会"幻觉"出一些根本不存在的函数。
后来我改了策略:配置文件只写100行左右的目录,指向各个详细文档。Agent启动时只加载目录,需要某个模块的细节时再按需读取。效果好得多。
为什么?因为有一条实测规律:上下文窗口用到大约40%的时候,Agent的输出质量就开始明显下降。推理不聚焦了,工具调用变差了,幻觉增多了。就像一个人读了一份超长报告,读到后面前面已经记不清了。Anthropic也发现了同样的问题——他们的模型在上下文快满时会变得犹豫,任务还没完成就提前收工了。他们管这叫"上下文焦虑"。
两个应对思路:一是按需给,不要一次性喂太多;二是及时重置——上下文快满时,把当前任务状态提取出来,开一个干净的新会话继续做。听起来粗暴,但Anthropic验证过了:干净的新会话往往比塞满历史的旧会话表现更好。他们的做法是把已完成工作、待办事项结构化提取出来,交给新会话继续。
说白了就是:让Agent待在干净、相关的上下文里,比喂更多信息重要得多。
写在文档里的规则等于没有-架构约束
"不要在UI层直接访问数据库"——写在文档里,Agent迟早会违反。不是不听话,是它记不住那么多规则。
正确做法:用工具代替文档。写一套自动检查规则,代码违反规范时自动报错,报错信息里直接告诉Agent怎么改。你可以把它理解成代码版的拼写检查——Word里拼错了会画红线,这里代码违规了会弹提示,不只告诉你"这里错了",还告诉你怎么改。Agent在修错的过程中被反复训练成更符合规范的写法。他们的原话很直接:"If it cannot be enforced mechanically, agents will deviate."——不能机械化执行的约束,Agent迟早会偏离。
约束分两层:软约束告诉Agent"应该怎么做"(文档、提示词),硬约束让它"只能这样做"(自动检查、结构测试、类型系统)。Harness靠的是硬约束。就像交通规则不能只靠自觉,得有摄像头和罚款。
一个实操经验:配置文件里每一行规则,最好都对应一个过去犯过的错误。Agent犯了一个新类型错误,就加一条规则。它不是静态文档,是持续积累的防错系统。犯过的错不再犯,就是进步。
做完不检查,等于没做-反馈循环
前面说的配置文件和自动检查,都是在Agent动手之前告诉它"应该怎么做"。但光有规则不够,你还得让Agent做完之后能发现自己哪里做错了。
想想你带新人的时候,光给他看编码规范没用,还得review他的代码。review的时候发现问题,告诉他怎么改,下次就不会犯同样的错。检查发现的问题,反过来更新规则,让同类问题以后不再出现。这就是一个自我改进的循环。Agent也一样——写完代码得跑测试、跑自动检查,发现问题就改,改完更新规则。
而且最好在提交之前就把问题拦截住。你在写代码的时候希望IDE即时标红,而不是等到上线后用户报bug——Agent也一样,能尽早发现问题,就不至于在错误的基础上越走越远。Stripe就是这么做的:每周产出1300多个完全由Agent生成的PR,质量靠的就是提交前自动跑检查、秒级修错,推送后再跑一轮完整的测试覆盖。
有个常见的坑:让Agent自己审查自己写的代码。它往往看一眼就说"做得不错"——就像让学生自己给自己打分,大概率打高分。Anthropic踩过这个坑,后来的做法是把活拆给三个Agent:一个负责规划要做什么,一个负责写代码,第三个专门负责审查。审查的那个不参与写代码,直接拿运行中的应用实际操作一遍,按功能、视觉、代码质量等维度打分。做的人和检查的人不是同一个,结果才靠谱。
Agent生成的速度有多快,代码腐化的速度就有多快-熵管理
AI生成的代码越多,重复逻辑、文档和代码不一致、没人用的死代码也跟着变多。这些混乱不会自己消失,只会越积越多。就像一个房间,每天往里放东西但从不整理,迟早没法用。
OpenAI踩过这个坑:3名工程师用Agent写了大约100万行代码,效率提升约10倍。但代价是AI生成物积累的混乱增长极快,一开始他们每周五花20%时间手动清理。后来发现不行,清理速度跟不上生成速度。最终的解法是专门弄一个后台Agent,定期扫描不一致和冗余,自动提交清理。
还有一个常见的混乱来源:Agent不知道代码库里已经有一个工具函数,就又写了一个。有人用16个并行Claude实例写一个C编译器,跑了约2000个会话,这个问题尤其严重。解法也是分出一个Agent专门做去重。
生成速度和清理速度要匹配。只管生成不管清理,项目会在自己的产出物里窒息。这也是为什么很多团队第一周觉得Agent特别好使,第三周就开始骂它——第一周混乱还没积累够,第三周已经到处是问题了。
用一个批量退款接口,把四个串起来
四个支柱不是各自独立,是一个循环。用一个具体场景串一遍:假设你要让Agent在现有的订单系统里加一个"批量退款"接口。
Agent启动,加载项目目录——代码分层结构、退款模块在哪、现有退款逻辑怎么写的。按需加载,不一次全读完。这是上下文工程。
开始写代码。后台实时检查:批量退款必须在Service层处理,不能在Controller里写业务逻辑;退款金额不能超过原价。违反立即报错,报错带修复建议。这是架构约束。
写完跑测试,发现并发退款可能重复退款。Agent根据测试输出加上了幂等性检查。然后另一个独立的审查Agent确认代码质量。这是反馈循环。
上线后后台定期扫描,发现批量退款方法和三个月前的单个退款方法有20行重复代码。自动提交去重PR。这是熵管理。
串起来就是:上下文决定Agent看到什么→约束限制它能做什么→反馈告诉它做对了没有→熵管理防止产出物把它淹没。每个支柱的输出,都强化下一个支柱的输入。
先做哪件?两件事见效最快
不要一上来就想搭齐四个支柱。我的建议是按顺序来。
先做两件事,投入不大但见效最快。第一,创建一个Agent配置文件(比如AGENTS.md),每次Agent犯错就更新它——这个文件会从几乎空白变成一份持续积累的防错清单。第二,搭一套代码自动检查,报错信息里直接告诉Agent怎么修,不是只说"这里错了"。
这两步做完了,Harness已经有了上下文和约束的基础。
然后补反馈循环:给Agent验证能力——让它能自己跑测试、看结果、根据结果修改。把反馈左移,在提交之前就拦截问题。控制上下文利用率,40%以上就触发压缩或重置。
最后补熵管理:定期跑扫描,清理重复代码、更新过时文档。有条件的话,让一个后台Agent专门做这件事。
还有一点容易被忽略:Harness不是搭好就完了,是持续的工程实践。模型会变强,旧的约束可能变成冗余。Anthropic把模型从Sonnet 4.5换成Opus 4.6后,原来必须分步检查的流程可以直接简化。定期回顾你的Harness——哪些规则已经不需要了?哪些检查可以简化?别让Harness自己也变成熵。
Prompt告诉Agent怎么说,Context告诉Agent看什么,Harness告诉Agent在什么条件下干活。如果你的Agent还在靠你反复纠正同一个错误,说明不是模型不行,是Harness没到位。
先把配置文件和代码自动检查搭起来,再逐步补反馈循环和熵管理。从小处开始,跑通了再扩展。
以上就是本篇的全部内容,欢迎留言探讨。
往期回顾:
让OpenSpec和Superpowers无缝配合的实现拆解,skill原文件全面开源
更多推荐
所有评论(0)