DeepSeek Harness:从固定内核到可塑运行时
摘要:DeepSeek Harness 的核心价值,是把 Agent harness 从固定内核推向可塑运行时。Cordis 管插件依赖和生命周期,Session log 保存运行事实。
DSH 关注的是替换边界
Agent 框架做到深处,会遇到一个很现实的矛盾:越想让能力可替换,运行时就越难保持确定。

图:可塑运行时让 Harness 的关键部件按场景替换
模型、工具、会话、存储、审批、上下文压缩、子任务编排都可能变化。
如果这些变化都写进固定内核,框架会越来越难改;如果全部放开成插件,系统又必须回答另一个问题:插件怎么安全组合,状态怎么恢复,副作用怎么清理,结果怎么解释。
DeepSeek Harness 的核心价值,正是在这个矛盾里把 Agent harness 从固定内核推向可塑运行时。它依赖 Cordis 管插件依赖和生命周期,用 Session log 保存运行事实。
前者回答“系统现在装成什么样”。后者回答“系统刚才做过什么”。
普通 coding agent 通常在固定 loop 外面加工具、Skill 和交互。需求只是“增加可执行动作”时,这条路最直接。
一旦要改变工具调度、上下文投影、终止条件、存储语义或会话隔离,扩展点就会进入 harness 内部。此时要让 runtime 的关键部件也能替换,并且替换后系统仍然可解释、可恢复、可评估。
DSH 的目标可以这样概括:让同一个 Agent 底座按场景动态组合能力。能力升级或替换后,系统仍能稳定运行,并能解释每一次结果从哪里来。

Cordis 的五个原则
Cordis 原本不是专为 Agent 设计的框架。它来自 Koishi 社区,是通用插件化组合框架。
DSH 借它把 Agent 能力组织成运行时插件图。
它的五个关键思想是:
| 原则 | 含义 |
|---|---|
| 插件即服务 | 插件提供某种 Service,并把生命周期挂到当前 context |
| 上下文即服务仓库 | 服务通过稳定的 ctx 键注册和查找,而不是直接 import 具体实现 |
| inject 声明依赖 | 插件声明所需服务,等依赖就绪后才激活 |
| 类型化事件通信 | 服务通过事件词汇观察、包装、扇出或顺序执行流程 |
| 可逆副作用 | 注册监听器、工具、句柄时同步登记 disposer,卸载时清理 |
这套设计的重点是运行时能沿依赖关系处理 Provider 变化:先停掉受影响的 Consumer,再在新依赖下重新激活。工具、监听器、后台任务这类已登记副作用,也应跟着 Fiber 生命周期逆序清理。
边界也要讲清楚:Cordis 能管理的是纳入 context 生命周期的副作用。数据库写入、远程调用、已发送消息、外部进程这类越界动作,仍然需要插件自己做幂等、补偿或人工确认。
七个核心问题
DSH 这套架构可以理解为对七类问题的连续回答。
| 问题 | DSH 的对应思路 |
|---|---|
| 如何让关键能力可替换 | 模型、工具、Session、Loop、存储等都通过 Service 暴露 |
| 如何让插件安全组合 | 用 inject、Fiber、Effect 和事件机制管理依赖与清理 |
| 如何让会话可持久化和恢复 | 用 append-only Session log 记录事实,再派生当前上下文 |
| 如何让工具执行可控 | 工具调用进入统一 pipeline,承接权限、审批、沙箱、结果处理 |
| 如何让 LLM 适配解耦 | LLM seam 统一不同 provider 的消息、流式和 tool call 语义 |
| 如何让 Agent 行为可编排 | Agent loop、subagent、workflow、goal 等以组合方式出现 |
| 如何让系统可观测、可调试 | 事件日志、runtime diagnostics、session query 支撑回放和定位 |
这些问题共同指向一个结论:Agent 框架真正难的部分,是变化之后还能不能知道系统是什么状态。
和其他 Harness 的差别
不同 harness 的差别不在于谁更高级。关键是扩展边界放在哪里。
| 方向 | 稳定内核 | 开放面 | 更适合的问题 |
|---|---|---|---|
| Codex CLI | Rust Agent 核心、工具执行、OS 沙箱 | MCP、Skills、Plugins、运行配置 | 安全稳定的自主编码执行 |
| Claude Code | 产品级 Loop、权限模型、会话工作流 | Skills、Hooks、MCP、Subagents、项目指令 | 深度开发者工作流 |
| Pi Harness v2 | 分层 Agent 核心、作业状态机、任务 DAG | Extensions、Tools、Providers、Lanes | 小内核上的定制和并行编排 |
| DSH | Cordis 组合协议、生命周期语义、Session 事实链 | Model、Tool、Session、Loop、调度、UI | 可重组、可演化的 Agent Runtime |
Pi v2 更像轻量 Agent Core 加用户态扩展系统。扩展可以注册工具、命令、模型 Provider、Prompt、Skill 和 TUI 能力,也可以通过 hook 影响上下文、工具调用和模型请求。
DSH 把扩展性下沉得更深。LLM、Tools、Agent Loop、Session、Persistence、Storage 都可以作为 Cordis Service 或插件存在,由 Fiber 管生命周期。
如果只是给 coding agent 增加一个命令、接入公司模型代理、加一个终端面板,Pi v2 这类用户态 API 更直接。如果不同租户需要不同 Session 实现、审批策略、存储后端或 Agent Loop,而且这些组合要能挂载、卸载、诊断和回滚,DSH 的服务模型才开始有优势。
LangChain 不在同一层
LangChain 和 LangGraph 也讲组合,但它们主要组合的是 Agent 应用如何执行。DSH 组合的是承载这些应用的 runtime。
| 比较维度 | LangChain / LangGraph | DeepSeek Harness |
|---|---|---|
| 组合单元 | 节点、Runnable、middleware、模型与工具路由 | Cordis 插件、服务定义、Provider、Consumer |
| 开放边界 | 编译后的 Agent 图和调用链 | 模型、工具、Session、Loop、存储、调度、UI |
| 生命周期 | 图执行、调用钩子、checkpoint 和显式清理 | 依赖驱动的加载/卸载,注册副作用逆序撤销 |
| 状态事实源 | 图状态与 checkpoint | append-only SessionEvent,模型可见内容可重建 |
| 主要目标 | 构建和编排 Agent 应用 | 构建可重组 Agent Harness |
要构建一个图式 Agent 应用,LangGraph 会更贴近问题。要承载多种 Agent,并按部署或会话替换 Loop、存储和调度,DSH 才值得进入比较范围。
第一道难题:运行时一致性
可塑运行时的底线,是相同目标配置最终应该收敛到等价状态。
这里的一致性不要求中间加载顺序完全相同。它要求系统静止后的可观察状态一致:没有旧服务、旧监听器和旧后台任务残留,也不会因为不同卸载路径得到不同 runtime。
Cordis 用 Fiber 管插件的一次运行实例,把注册动作和清理动作绑定到同一生命周期。当依赖服务被替换,消费方先停用旧状态,再在新依赖下重新激活。

这项能力有前提:依赖关系不能卡死,Fiber 激活产生的 effect 要有界,插件必须完整登记清理动作。越过 context 边界的副作用,仍然要靠外部幂等或补偿机制。
第二道难题:可解释和可证伪
Agent 出错后,工程师真正需要知道的是“当时系统给了模型什么条件”。
一次请求至少要能还原:
- 启用了哪些插件和 Provider
- 模型实际看到了哪些消息
- system prompt 是怎么渲染出来的
- 工具 schema 和调用参数是什么
- 哪些工具调用成功、失败、超时或被拒绝
- 会话历史在何时被压缩、替换或分叉
Trace 能回答“这次执行经过哪些节点”。要解释这些输入是怎么形成的,就需要 append-only Session log。
Session log 是事实链,不是普通聊天记录。模型可见历史从事件日志投影出来。
压缩时不改写过去,而是追加 replacement 节点,改变当前 surface,同时保留原始事件。
可重建只能回答“当时发生了什么”。要证明“这样改之后确实更好”,还需要另一套评测:独立任务集、固定 evaluator、明确基线版本,以及和候选配置分开保存的证据。
否则,配置生成、任务选择和评分都被同一条链控制,偶然波动也可能被误判成进步。
Cordis 和 Session 各管一半
DSH 没有试图用一个状态模型解决所有问题。它把运行时治理拆成两半:
| 事实面 | 负责什么 | 害怕什么 |
|---|---|---|
| Cordis | 当前系统装了什么、依赖是否满足、变更后能否清理 | 清理失败、残留旧状态、依赖图不可收敛 |
| Session log | 运行中发生了什么、模型看到了什么、能否恢复和回放 | 日志缺失、投影漂移、事件无法解释 |
Unified Context 像一张运行时底图,记录哪些服务已经挂上,哪些插件依赖这些服务。Revertible Effects 负责把注册项和清理动作绑定。Reactive Coeffects 负责在依赖变化后只重载受影响的组件。
Session log 则保存另一类事实:turn、step、用户消息、assistant chunk、assistant message、tool call、tool result,以及会话压缩和替换关系。它让恢复、分叉、回放和 UI 视图都从同一条事实链派生,避免多份“当前状态”各自漂移。
结语
DeepSeek Harness 的方向,是让 harness 本身可以被组合、替换和治理。
这条路有清晰价值:多 Provider、多会话隔离、多 runtime 组合、多插件生态这些问题,固定内核很难长期扛住。
DSH 用 Cordis 管运行时拓扑,用 Session log 管执行事实,给可塑 Agent Runtime 提供了基础。
它的边界同样清楚。Cordis 不提供操作系统级沙箱,不保证外部副作用可撤销;Session log 能重建事实,不自动证明效果提升。
只有当组合压力真的成为主要矛盾时,完整 DSH 才值得采用。否则,先借鉴能力 seam、生命周期清理和事件事实链,通常比直接迁移整套框架更稳。

推荐阅读
Prime Agent 把 Coding Agent 从工具调用推向可恢复工作流

浙公网安备 33010602011771号