Harness 工程说白了,就是围着模型搭系统,把它变成能真正干活的引擎。模型本身是有智能的,但得靠 Harness,才能让这份智能真正用起来。这篇文章先跟大家说清楚什么是 Harness,再从模型这个最基本的出发点,一步步推导出现在以及未来 Agent 最核心的组成部分。
01
有没有人能把 Harness 讲明白?其实特简单,Agent = Model + Harness。要是你没在做模型训练,那你干的活儿,多半都属于 Harness 的范畴。说白了,Harness 就是:所有不属于模型本身的代码、配置,还有执行逻辑,都算。一个光秃秃的模型,可算不上 Agent;只有等 Harness 给它配上状态管理、工具调用能力、反馈循环,还有可执行的约束,它才算真正的 Agent。说得再具体点,Harness 一般包括这些东西:系统提示词、工具与技能(还有 MCP)以及它们的说明、封装好的基础设施(比如文件系统、沙箱、浏览器)、编排逻辑(像子 Agent 的生成和交接、模型路由这些),还有用来保证执行稳定的 Hook(钩子机制)或者中间件(比如上下文压缩、续写机制、Lint 检查之类的)。在实际的系统里,模型和 Harness 的边界其实有好多种划分方式,而且往往没那么清晰。但从做工程的角度来看,咱们刚才给 Harness 下的定义,区分度是最高的——因为它逼着我们从“怎么围绕模型的智能来设计系统”这个角度去思考问题。接下来,咱们就从模型这个最基础的抽象概念入手,一步步说说这些 Harness 组件到底为啥会存在。
02
为啥需要 Harness 呢?因为我们希望 Agent 能做到的很多事,模型本身其实根本做不到,这就是 Harness 存在的意义。大多数情况下,模型就是接收文本、图像、音频、视频这些输入,然后输出文本(或者结构化的调用结果),就这么点事儿。默认情况下,它做不到这些:在多次交互之间,维持持久的状态;执行代码;获取实时信息;搭建运行环境,还要安装依赖。这些能力,全都是 Harness 层来提供的。LLM 的结构就决定了,必须有一层外部机制把它包起来,它才能真正参与到实际工作里来。举个简单的例子,咱们平时用的聊天产品,其实就是用一个 while 循环来保存历史消息,然后不断追加新的用户输入。几乎所有人都用过这种形式的 Harness,本质上,我们做的就是把希望 Agent 表现出来的行为,变成 Harness 里的具体实现。
03
从目标行为反推 Harness 设计
Harness 工程的作用,就是帮我们把有用的先验知识加进去,从而引导 Agent 的行为。随着模型能力越来越强,Harness 也慢慢被用来以更精细的方式,扩展或者修正模型,让它能完成以前很难做到的任务。咱们不打算把所有可能的 Harness 功能都列出来,这里的目标是,从“让模型能完成实际工作”这个出发点,推导出一组关键能力。核心思路很简单:我们想要(或者需要修正)的行为,决定了对应的 Harness 该怎么设计。
04
用文件系统实现持久存储和上下文管理
我们希望 Agent 能有持久化存储的能力,用来处理真实的数据、转移那些装不下上下文的信息,还能在不同的会话之间继续推进工作。但模型只能直接处理它上下文窗口里的信息。在引入文件系统之前,用户只能靠复制粘贴,把内容提供给模型,既麻烦又低效,也不适合自动化的 Agent。现实世界里,我们本来就是靠文件系统来组织工作的,而且模型在训练的时候,也学到了这种模式。所以一个很自然的解决方案就是:让 Harness 提供文件系统的抽象,还有相关的操作工具。文件系统可以说是最基础的 Harness 原语之一,它能带来好几个关键能力:Agent 有了一个工作空间,可以读取数据、代码和文档;信息可以一步步写入或者转移,不用全都堆在上下文中;中间结果能保存下来,这样就能维持跨会话的状态;文件系统还是个天然的协作界面,多个 Agent 或者人和 Agent 之间,都能通过共享文件来配合工作,比如 Agent Teams 这种架构,就离不开这一点。要是再加上 Git,文件系统还能拥有版本控制的能力,Agent 就能跟踪工作进度、回滚错误,还能做分支实验。后面咱们还会提到文件系统,因为它其实是很多其他能力的基础。
05
用 Bash 和代码执行作为通用工具
我们希望 Agent 能自己解决问题,而不是每一步都要依赖我们预先定义好的工具。现在主流的 Agent 执行模式是 ReAct 循环:模型先思考推理,然后通过调用工具执行动作,观察结果,再进入下一轮循环。问题在于,Harness 只能执行我们事先定义好的工具。与其给每一种可能的操作都写一个专用工具,不如直接提供一个通用工具,比如 Bash。所以,Harness 通常都会提供 Bash 能力,让模型通过编写和执行代码来解决问题。Bash 加上代码执行,就相当于给模型配了一台“通用计算机”。模型可以通过写代码临时搭建工具,再也不用被固定的一组预配置工具限制住。当然,Harness 还是会提供一些其他的专用工具,但代码执行正慢慢变成 Agent 自主解决问题的默认方式。
06
用沙箱和工具完成执行与验证
Agent 得有个合适的环境,才能安全地执行操作、观察结果,还能持续推进任务。咱们已经给模型提供了存储能力和代码执行能力,但这些都得在具体的环境里才能实现。直接在本地运行模型生成的代码,风险挺高的,而且单一的环境也很难支持大规模的任务。沙箱就提供了一个隔离又安全的执行环境。Harness 可以把执行过程放到沙箱里,让 Agent 在里面运行代码、访问文件、安装依赖,完成任务。为了进一步提高安全性,还可以引入命令白名单机制,限制网络访问。与此同时,沙箱还能带来很好的可扩展性:环境可以按需创建,能并行运行多个任务,任务完成后还能销毁。一个完善的环境,通常还需要预先配置好常用的工具,比如语言运行时、依赖包、Git、测试工具,还有用来做网页交互的浏览器。浏览器、日志、截图、测试运行器这些能力,能让 Agent 观察并分析自己的行为,从而形成一个自验证循环:写代码 → 运行测试 → 分析结果 → 修复问题。要注意的是,这些环境配置,模型本身是不会做的。Agent 在什么地方运行、有哪些工具可用、能访问哪些资源、怎么验证结果,这些全都是 Harness 层的设计决策。
07
用记忆与搜索实现持续学习
我们希望 Agent 能记住自己的经历,还能获取到它训练之后才出现的信息。模型本身只有权重和当前的上下文,没有额外的记忆。在不修改权重的前提下,增加知识的主要方式,就是把知识注入到上下文中。在记忆这方面,文件系统又一次成为了核心。Harness 可以支持类似 AGENTS.md 这样的记忆文件,在 Agent 启动的时候,把这些文件加载到上下文中。随着 Agent 不断更新这些文件,系统就会持续注入最新的内容,这样就形成了一种“持续学习”的机制。另外,模型有个问题,就是有知识截止期,没法直接获取训练之后的数据,比如那些更新后的库版本。所以,得靠 Web 搜索和 MCP 工具(比如 Context7),让 Agent 拿到超出训练范围的信息。所以说,Web 搜索以及动态获取最新上下文的能力,也是 Harness 里特别关键的一类基础能力。
08
对抗 Context Rot(上下文退化)
我们不希望 Agent 在执行过程中,性能越变越差。所谓 Context Rot(上下文退化),就是说随着上下文窗口被越填越满,模型在推理和完成任务时的表现会慢慢变差。上下文是有限又宝贵的资源,所以 Harness 必须好好管理它。其实从某种角度来说,现在很多 Harness 相关的工作,本质上都是在做“上下文工程”。当上下文快到上限的时候,就得进行压缩。要是不处理,一旦超过上下文限制,API 可能就直接报错了,这在工程上是绝对不能接受的。所以 Harness 通常会通过总结和转移的机制,让 Agent 能一直运行下去。如果工具调用产生了大量输出,全都放进上下文里,会引入很多没用的噪声。常见的做法就是,只保留开头和结尾的一部分内容,剩下的都写到文件系统里,需要的时候再读出来。除此之外,要是在启动的时候加载太多工具或者 MCP 服务,一开始就会拖慢模型的表现。Skills(按需加载的能力模块)就是通过渐进式加载,来缓解这个问题的。模型本身不会主动选择加载哪些能力,但 Harness 可以用这种方式保护上下文,避免它过早退化。
09
长时间尺度上的自主执行
我们希望 Agent 能在比较长的时间里,自动、稳定地完成复杂任务。自动化软件开发,算是编码类 Agent 的一个重要目标。但现在的模型还有些局限,比如容易提前停止、不会拆解复杂任务,还有在跨多个上下文窗口的时候,表现不稳定。所以,一个好的 Harness,必须围绕这些问题来设计。到这时候,前面提到的那些能力就开始协同发挥作用了。长时间的任务,需要持久的状态、规划能力,还有观察和验证机制,才能跨多个上下文持续推进。文件系统和 Git 是用来跨会话跟踪工作的。长期任务可能会产生几百万个 token,文件系统能稳定记录这些过程,而 Git 能让新的 Agent 快速搞懂当前的状态和历史情况。对于多 Agent 协作来说,文件系统也是一个共享的“账本”。Ralph Loop 是用来让任务持续执行的。这是一种 Harness 模式:通过 Hook 拦截模型的“结束”行为,然后在新的上下文窗口里,重新注入原始目标,逼着任务继续推进。这里面文件系统起到了关键作用,因为每一轮都能在新的上下文中,读取之前的状态。规划和自验证是用来保持方向的。规划就是把目标拆成好几个步骤,Harness 可以通过提示词和文件机制,支持这个过程。每完成一步,就通过测试或者自评来验证;要是失败了,就通过 Hook 把错误反馈给模型,进入下一轮迭代。验证不仅能提高结果的可靠性,还能给模型提供持续改进的信号。
10
Harness 的未来
模型训练与 Harness 设计正在逐渐耦合
有些 Agent 产品(比如 Claude Code、Codex),已经在训练阶段就把 Harness 纳入了闭环,让模型在文件系统操作、Bash 执行、规划以及多 Agent 协作方面,表现得更好。这就形成了一个反馈循环:先在 Harness 里找到有效的模式,再把它加到训练里,进而进一步增强模型的能力。但这种共同演化也带来了问题,比如泛化能力下降。当工具逻辑发生变化时,模型的性能可能会明显下降,这说明模型在一定程度上,“过拟合”了训练时用的 Harness。不过,这并不意味着某个模型对应的 Harness,就是最好的选择。实际上,在不同的 Harness 下,同一个模型的表现可能差别很大。比如在 Terminal Bench 2.0 上,我们就看到了明显的性能波动;甚至只要调整一下 Harness,就能把一个编码 Agent 的排名,从 Top 30 提升到 Top 5。这说明,Harness 还有很大的优化空间。
Harness 工程会走向哪里?
随着模型能力不断增强,一些现在属于 Harness 的能力,可能会慢慢被模型吸收,比如规划、自验证以及长程一致性,这样就能减少对上下文注入的依赖。这看起来好像是说,Harness 会变得没那么重要。但就像 Prompt 工程到现在依然重要一样,Harness 工程大概率也会长期存在。因为它不只是在弥补模型的不足,更重要的是围绕模型的智能,搭建完整的系统。好的环境配置、合适的工具、持久的状态以及验证机制,不管模型智能水平怎么样,都能让它变得更高效。目前,Harness 工程还是一个非常活跃的研究方向。比如在 LangChain 的 deepagents 项目中,人们正在探索:如何让上百个 Agent 在同一代码库上并行协作如何让 Agent 分析自身执行轨迹,从而发现并修复 Harness 层问题如何根据具体任务动态组装工具与上下文,而不是预先配置一切这篇文章本质上就是在回答两个问题:什么是 Harness,以及它如何被我们对模型能力的期待所塑造。模型提供智能,而 Harness 让这种智能真正发挥作用。愿我们能搭建出更好的 Harness、更完善的系统,还有更强大的 Agent。如果你已经看到这里,其实你已经踩进门槛里了。剩下的,就是把这些“理解”,变成“能做出来”的东西。