$dshubuser@dshub:~/plugins$
  • 插件
  • 提交插件
  • 博客
Cordis:把运行中的应用变成一棵可逆的插件树
2026/08/18

Cordis:把运行中的应用变成一棵可逆的插件树

从 cordis.yml、Loader 和 Context 开始,理解 Cordis 如何让 DeepSeek Harness 组合、替换并安全卸载运行时能力。

短结论:Cordis 把启动、依赖和清理拆成三个运行时责任:Loader 负责组合,Context 负责连接,Fiber 负责拥有并撤销插件副作用。

如果只记住一个画面,请看上方的头图:一行 cordis.yml 经过 Loader 进入 Context,最后变成一个可以运行、替换和卸载的 Fiber。下面用四张源码驱动的流程图把这件事讲清楚。

01 / 一行配置如何进入运行时

Cordis 从 cordis.yml 到 Loader、Context、inject 和 ACTIVE Fiber 的组合流程图

这条链路来自 Cordis 教程的启动器:根 Context 被创建后,Loader 读取当前目录的 cordis.yml,再把配置中的模块挂载进运行时。配置决定组合,插件决定贡献,Fiber 记录这一次挂载的所有权。

- id: hello
  name: './hello.ts'

插件只需要贡献自己的入口:

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

export function apply(ctx: Context) {
  console.log('hello from my first plugin')
}

02 / 插件树解决哪三个问题

需求Cordis 的动作运行时结果
增加能力在组合层增加插件行不改中央启动入口
替换实现消费者依赖服务名,不依赖文件provider 可替换
回收副作用Fiber 卸载时执行 disposers监听器、注册和资源不残留

重点不是“插件”这个名词,而是每个插件实例都有明确的运行时所有权。这也是 Cordis 不只是模块加载器的原因:代码被找到之后,还要知道依赖何时满足、资源由谁清理。

03 / Context 是连接层,不是全局变量

DeepSeek Harness 中 Cordis Context 连接 tools、llm、agents 和 sessions 服务的关系图

Context 同时提供服务访问和插件注册。DSH 中的 ctx.tools、ctx.llm、ctx.agents 与 ctx.sessions 都是按名称连接的能力;消费者不需要直接导入某个 provider 的实现类。

当插件通过 inject 声明服务依赖时,Cordis 会让它停留在 PENDING,直到依赖可用后再进入 LOADING。启动时机因此由依赖关系决定,而不是由配置文件的偶然顺序决定。

04 / 换 provider,不换 consumer

Cordis 通过 shell 服务名替换本地 provider 与 E2B provider 的流程图

消费者只声明能力名称:

- id: terminal-tool
  name: './terminal-tool.ts'
  inject: ['shell']

组合层可以把 shell 指向本地实现,也可以指向 E2B 实现。消费者代码仍然依赖同一个服务名,这正是 DSH profile 可以选择不同运行时提供方的基础。

05 / HMR 的核心是 Fiber 可逆

Cordis Fiber 从 PENDING 到 ACTIVE、UNLOADING、DISPOSED 的生命周期流程图

HMR 不是再次 import 文件,而是先卸载旧 Fiber,再挂载新 Fiber。Cordis 的生命周期状态包含 PENDING、LOADING、ACTIVE、FAILED、UNLOADING 和 DISPOSED;图中每个状态都对应一次可观察的运行时阶段。

外部资源通过 effect 交给 Fiber 管理:

ctx.effect(() => {
  const timer = setInterval(() => console.log('tick'), 200)
  return () => clearInterval(timer)
})

主体创建资源,返回的 disposer 在卸载时撤销资源。ctx.on()、ctx.plugin() 和服务注册也遵循同一套可逆关系。

06 / 这就是 DSH 的组织方式

在 DeepSeek Harness 中,模型适配器、工具、会话、agent 管理和 agent loop 都以插件进入运行时。可以把它压缩成四个词:

  • 配置选择组合:profile 决定加载哪些插件。
  • Context 连接能力:服务定义、provider 和 consumer 通过名称协作。
  • Fiber 拥有实例:每次挂载都有独立生命周期。
  • effect 撤销副作用:卸载不是约定,而是运行时动作。

所以“一切皆插件”不是目录结构,而是替换位置和资源所有权都显式可见。

下一步怎么读

  1. 第一个插件:hello.ts + cordis.yml
  2. 生命周期与 effect
  3. 服务与 inject
  4. 组合与 HMR

实现依据:Loader 启动器、Context、Plugin registry、Fiber lifecycle 与 Cordis primer。

全部文章

作者

avatar for DSH Research
DSH Research

分类

  • Agent 基础设施
01 / 一行配置如何进入运行时02 / 插件树解决哪三个问题03 / Context 是连接层,不是全局变量04 / 换 provider,不换 consumer05 / HMR 的核心是 Fiber 可逆06 / 这就是 DSH 的组织方式下一步怎么读

邮件列表

加入我们的社区

订阅邮件列表,及时获取最新消息和更新

[dshub] [zsh]$ dshub ls$ dshub submit$ dshub blog
-- NORMAL -- ✓ 2026 dshub