OpenCode Dev 源码拆解¶
先给结论¶
OpenCode 的核心不是“一个更大的 Agent Loop”,而是把 Agent 执行拆成了几个可以分别替换、持久化、回放的层:
- Schema / Protocol 描述跨进程的数据形状和事件语义。
- Core 提供 Location-scoped 的领域服务:Session、Project、Provider、Tool、Database、Context。
- OpenCode Server 把这些服务装进 Effect runtime,并暴露 HttpApi、SSE/WebSocket 和 CLI。
- Client / SDK 把 API 变成稳定的调用边界,TUI、Web、Desktop、ACP 都消费这条边界。
- Session Runner 负责把 durable input 推进为 provider turn,再把模型事件和工具结果写回历史。
这套设计解决的是一个比“调用模型”更难的问题:当用户打开多个项目、网络失败、工具运行很久、上下文超过窗口、UI 断开再连接时,Agent 仍然要能正确继续。
一条 Prompt 的总旅程¶
flowchart LR
A[CLI / TUI / Web / SDK] --> B[HttpApi Session endpoint]
B --> C[SessionInput durable inbox]
C --> D[SessionExecution wake]
D --> E[SessionRunner drain]
E --> F[System Context + Session History]
F --> G[LLM canonical request]
G --> H[Provider adapter]
H --> I[streamed LLM events]
I --> J[EventV2 + Session projection]
J --> K{tool call?}
K -->|yes| L[Permission + Tool Registry]
L --> M[tool result / output file]
M --> E
K -->|no| N[SSE / Sync / UI projection]
图中最重要的箭头是 C → D → E:输入先被接受并持久化,执行是随后发生的 advisory wake。这样“请求已经被系统接受”和“当前进程是否正在执行”不会混成一个状态。
这份拆解怎么读¶
每章都保持四个层次:
- 是什么:给出术语、边界和数据流。
- 怎么做:指出包、目录、入口函数和关键类型。
- 为什么这样做:解释依赖方向、失败模型、持久化和 UI 解耦的取舍。
- 读源码顺序:避免在 400 多个文件里随机跳转。
推荐顺序是先读 01 总览 和 02 分层,再按执行链阅读 03 Server 与 API → 04 Session V2 → 05 上下文工程 → 06 LLM 与 Provider → 07 工具与安全。最后再看事件、存储和 UI。
关于 V1 / V2
本拆解明确区分 legacy V1 和 Session V2。当前源码仍能看到 packages/opencode/src/session/* 的 V1 兼容服务,以及 packages/core/src/session/* 的 V2 durable runner。不要把两个 Session 名字当成同一套实现;V2 的目标是持久化输入、位置作用域、可重放事件和更清晰的 provider-turn 边界。
与 Pi-Agent 拆解的对应关系¶
| Pi-Agent 的问题 | OpenCode 中的对应物 | 关键差异 |
|---|---|---|
| Agent Loop | SessionRunner + SessionExecution |
Loop 不再是单个内存函数,而是 durable drain |
| 模型调用 | @opencode-ai/llm + Provider catalog |
额外处理 provider 原生 continuation、认证、模型路由 |
| 工具系统 | Core Tool Registry + Permission + ToolOutputStore | 工具输出和授权也是持久化/可观测边界 |
| 消息系统 | Schema Message / V1 projection / V2 history | 面向 API、数据库、LLM、UI 有不同投影 |
| 事件驱动 | Event V2 + projectors + SSE/sync | 事件既是通知也是回放输入 |
| 上下文工程 | System Context + Context Epoch + compaction | 初始系统上下文与中途更新被严格分离 |
| 会话管理 | Project / Location / Workspace / Session | 一台 server 管多个项目和 worktree |
源码快照和证据等级¶
文中“源码事实”都对应本地快照中的文件路径;设计意图优先参考仓库中的 AGENTS.md、CONTEXT.md、specs/ 和注释。上游官网文档用于确认用户可见语义,不用于替代源码分析。