DeepSeek Harness 是什么

DeepSeek Harness(命令行前缀 dsh)是 DeepSeek AI 开源的 Agent Harness(智能体运行壳)。

它不是单纯的聊天网页,也不只是「调用 DeepSeek API 的封装」。它提供的是模型外面的一整层运行时:

  • Agent 循环(模型决策 → 调工具 → 继续)
  • 工具注册与执行
  • 会话日志与续跑
  • 权限与审批策略
  • Web UI / CLI / SDK 等入口

当前状态是 developer preview(开发者预览版),会持续快速迭代,并可能有破坏性变更。

官方文档与仓库:

  • 文档:https://deepseek-harness.github.io/deepseek-harness/
  • 仓库:https://github.com/deepseek-ai/deepseek-harness

核心原理:万物可插件

DeepSeek Harness 最鲜明的设计原则是:

Everything is a plugin(万物皆插件)

这句话不是宣传语,而是架构约束。含义是:

在 dsh 里,没有必须被改核心源码才能扩展的「特权内核」。

模型适配、工具注册、会话存储、系统提示、Agent 循环驱动……这些都可以看成插件,挂在同一个运行时上下文上,从配置里组合出来。

用官方架构文档的说法:

  • 底层框架是 Cordis
  • 插件贡献服务、类型化事件、可回滚的副作用
  • 模型适配器、工具注册表、会话日志、甚至 Agent 循环本身,都是插件
  • 扩展 dsh 的方式,是在旁边挂载另一个插件,而不是打补丁改核心

可以把它想成:

传统做法:
  改核心 → 升级冲突 → 分叉维护 → 很快烂掉

dsh 的做法:
  核心只是组合器
  能力 = 按顺序叠起来的插件层
  需要什么,就插入什么插件

为什么「没有特权核心」重要

很多 Agent 框架最终都会遇到同一个问题:

  1. 你想加一个自定义能力
  2. 官方核心没有预留接口
  3. 你只好 fork 仓库、改内部代码
  4. 上游一升级,你的分叉就痛苦

dsh 想避开这条路。它把产品做成一棵 启动时组合出来的插件树:

  • Profile(配置档):一组命名组合,决定你启动的是 Web、headless、SDK 还是 ACP
  • Bundle(分发包):一组可被上层继续 patch 的配置行 + 挂载代码
  • Patch(补丁层):按 id 替换某行配置,或插入新插件

于是「加能力」变成「往配置里插入一行」,而不是「改源码」。


插件在 dsh 里长什么样

Harness 插件通常是一个导出 apply(ctx) 的模块。框架加载插件时传入共享上下文 ctx,你在里面注册能力:

import type { Context } from '@deepseek-ai/cordis'

export const name = 'hello-plugin'

export function apply(ctx: Context) {
  console.log('[hello-plugin] plugin loaded!')
}

这就是最小完整形态。没有额外样板文件,没有必须继承的基类。

如果插件依赖别的服务(例如工具注册表),用 inject 声明:

export const inject = ['tools']

export function apply(ctx: Context) {
  // 此时 tools 服务已就绪
}

框架会等依赖就绪后再调用 apply。插件卸载时,经由 ctx 注册的监听器、工具、定时器会自动清理;需要显式释放的资源(如连接)可用 ctx.effect() 提供销毁函数。


万物可插件:具体包括哪些东西

按官方架构说明,至少这些都可以插件化:

能力说明
模型适配接入 DeepSeek 或其他 OpenAI 兼容端点
工具定义模型可调用的函数
系统提示提示片段与工具 schema 的组装
会话日志追加式事件日志,作为上下文来源
Agent 循环默认驱动实现,也可换
文件系统 / 沙箱执行环境与权限边界
Shell / 终端命令执行与持久终端
子 Agent委派与协作
Webhook / 自动化从外部触发会话

设计上的关键判断是:扩展点是事件与服务,而不是改循环源码。

例如:

  • 加模型 → 在模型适配缝上注册
  • 加工具 → 在工具注册表上注册,schema 自动进入提示组装
  • 拦截一次工具执行 → 监听工具相关事件
  • 换存储后端 → 实现会话持久化接口

一次插件工具注册(概念示例)

import type { Context } from '@deepseek-ai/cordis'
import { defineTool } from '@deepseek-ai/dsh-tools'

export const name = 'greet-tool'
export const inject = ['tools']

export function apply(ctx: Context) {
  ctx.tools.register(defineTool({
    name: 'greet',
    description: 'Greet someone by name.',
    parameters: {
      name: { type: 'string', required: true, description: 'The name to greet' },
    },
    async execute(args) {
      return `Hello, ${args.name}!`
    },
  }))
}

这里体现的正是「插件化」:

  1. 工具不是写死在产品里
  2. 插件把自己注册进工具子系统
  3. 循环、提示、UI 不需要各自知道这个工具从哪来

和「普通 Agent 框架」的差别(概念上)

很多框架也允许加插件,但产品主体仍是一坨不可替换的 monorepo 核心。

dsh 更极端一点:

普通框架:
  核心很大,插件是外挂

dsh:
  连核心循环、模型适配、会话都可以看成可替换插件
  你看到的「产品」只是默认组合结果

所以它更适合两类人:

  1. 想做 可深度定制 Agent 运行时 的开发者
  2. 想把同一套能力,组合成 Web / CLI / SDK / 自动化服务的人

如何开始体验

官方 Web UI 路径(需 Node.js 环境):

npx @deepseek-ai/dsh web

然后大致流程:

  1. 打开本地 Web UI
  2. 在设置里配置 DeepSeek API Key
  3. 选择一个工作区(项目目录)
  4. 创建会话并下发任务

示例任务:

Summarize this repository and identify its main packages.

Agent 可以读取工作区文件、运行命令、委派工作并维护计划;需要审批的操作会先询问。

也可以从源码启动:

git clone https://github.com/deepseek-ai/deepseek-harness.git
cd deepseek-harness
pnpm install
pnpm run build
pnpm dsh web

注意: 这是 developer preview,请先阅读仓库里的安全说明,不要一上来对高权限环境开跑。


使用时要建立的心智模型

理解 dsh,建议按下面三层看:

1. Cordis
   插件运行时:服务、事件、生命周期、可回滚副作用

2. Harness 组合层
   profile + bundle + patch → 启动时变成一棵插件树

3. 产品入口
   web / headless / sdk / acp 只是不同的默认组合

当你想「加一个能力」时,先问:

  1. 这是工具?
  2. 这是模型适配?
  3. 这是执行环境?
  4. 这是会话/持久化?
  5. 这是只挂一次的 UI 扩展?

答案决定你挂到哪条缝上,而不是直接去改 Agent 循环。


局限与预期

  • 变更快:preview 阶段,API 与配置格式可能破坏兼容
  • 有学习成本:需要理解 Cordis 的服务/事件模型
  • 不是开箱即用的聊天产品:它更像给开发者的 harness
  • 插件生态还在成长:很多能力仍要自己写

总结

DeepSeek Harness 的核心主张可以压缩成三句:

  1. 它是 Agent Harness:管模型外面的运行层,而不只是管一次聊天补全
  2. 万物可插件:模型、工具、会话、循环都可替换组合
  3. 没有特权核心:扩展方式是挂载插件与配置层,而不是永久分叉源码

如果你在做 Agent 基础设施,或想理解「harness」如何被做成可组合系统,dsh 是一个值得拆开看的样本。

后续可深入的方向:

  • 自定义插件与工具 DSL
  • 模型适配缝
  • 权限、沙箱与审批策略
  • 会话日志如何成为上下文真源