mirror of
https://github.com/deepseek-ai/deepseek-harness
synced 2026-08-15 21:04:50 +00:00
3.0 KiB
3.0 KiB
可组合性与插件系统
组合
编程的本质就是组合。将小的构建块拼装为更大的系统,再将大系统作为块继续拼装——这是从函数到模块到微服务一脉相承的思想。
组合可以分为两种:
- 静态组合:编译期确定的组合,例如函数调用、模块导入。
- 动态组合:运行时确定的组合,例如热更新、插件加载/卸载。
静态组合是逻辑的组合;动态组合为可组合性引入了时间和空间两个新维度。
三种可组合性
| 维度 | 定义 | 对应问题 |
|---|---|---|
| 逻辑可组合性 (Logical) | 功能能否被任意拆分和组装 | 接口设计是否正交 |
| 时间可组合性 (Temporal) | 能否灵活、安全地控制组合的运行时序 | 能否热加载/卸载而不泄漏 |
| 空间可组合性 (Spatial) | 能否灵活、安全地管理组合的依赖关系 | 依赖缺失时行为是否确定 |
一门编程语言或应用框架越多地使用组合范式,就称它的可组合性越好。
传统插件系统的问题
插件系统是动态组合的典型形式。浏览器扩展、IDE 插件、操作系统驱动,都是其实例。然而大多数插件系统并不可靠。
不可逆的插件化
以 VSCode 为例:
- 卸载或更新插件时需要重启整个系统。
- 无法在运行时追踪和回收副作用,导致内存泄漏和非预期的资源占用。
- 即便提供了
deactivate钩子,也无法强制开发者正确实现清理逻辑。
根本原因:未做到时间可组合——系统不知道某个插件产生了哪些副作用、占用了哪些资源。
不完全的插件化
- 无法表达插件间的依赖关系,扩展能力受限。
- 只有外围功能被下放给插件,核心功能依然通过修改主体代码来实现。
根本原因:未做到空间可组合——系统缺乏对依赖关系的建模和管理。
Cordis 的解法
Cordis 同时解决了上述两个问题:
- 可逆作用 (Revertible Effects) 实现时间可组合性——所有注册自动追踪、自动回收。
- 响应式余作用 (Reactive Coeffects) 实现空间可组合性——依赖声明驱动加载顺序。
两者通过上下文模型 (Context Model) 统一为单一的编程范式:开发者只需通过 ctx 调用框架 API,可逆性和依赖管理由框架保证。
在 Harness 中的体现
DeepSeek Harness 将 Cordis 的可组合性应用到 Agent 开发领域:
// 一个 Harness 插件天然是可逆的
export const inject = ['tools', 'llm'] // 空间可组合:声明依赖
export function apply(ctx: Context) {
// 时间可组合:注册会被自动追踪和回收
ctx.tools.register(defineTool('my-tool', {
description: '...',
parameters: { /* ... */ },
async execute(args) { /* ... */ },
}))
}
插件卸载时,tool 自动注销、事件监听自动移除——无需手动清理。依赖的服务(如 llm)消失时,插件自动挂起;恢复时自动重新加载。