OpenClaw 源码全链路拆解笔记
OpenClaw 源码全链路拆解笔记
从一条 “你好” 消息出发,追踪 OpenClaw 处理消息的完整路径。
目录
- 架构总览
- 第 1 站:入口与网关启动
- 第 2 站:消息接入与标准化
- 第 3 站:路由决策 — 谁来处理这条消息?
- 第 4 站:会话初始化与上下文装配
- 第 5 站:执行配置与任务排队
- 第 6 站:Agent Runner — 生命周期管理
- 第 7 站:执行层 — Fallback 与容错
- 第 8 站:嵌入式运行时 — 模型解析与认证
- 第 9 站:核心推理 — 真正调用大模型
- 第 10 站:回复分发 — 消息送达用户
- 核心子系统
- 设计模式总结
- 关键洞察
架构总览
第 1 站:入口与网关启动
核心问题:OpenClaw 是如何启动的?
进程入口
src/entry.ts— CLI 入口,解析命令行参数,启动子命令src/gateway/boot.ts— Gateway 启动引导,执行BOOT.md
Gateway Server 启动
src/gateway/server.impl.ts#L343—startGatewayServer()核心启动函数- 加载配置
src/config/config.ts→loadConfig() - 启动 WebSocket 服务
src/gateway/server/ws-connection.ts - 启动 HTTP 端点
src/gateway/server-http.ts - 注册所有 RPC 方法
src/gateway/server-methods.ts - 创建 Channel Manager
src/gateway/server-channels.ts - 初始化 Cron 服务
src/cron/service.ts - 启动 Plugin 系统
src/gateway/server-plugins.ts
- 加载配置
配置系统
src/config/config.ts— 配置导出总入口src/config/io.ts— 配置读写、缓存、运行时快照src/config/types.ts—OpenClawConfig完整类型定义src/config/validation.ts— 配置校验src/config/sessions/— 会话存储管理
💡 你会学到
Gateway 不是一个简单的 HTTP server——它是整个系统的控制平面。所有消息渠道、工具、Agent 都挂载在 Gateway 上。
第 2 站:消息接入与标准化
核心问题:不同平台的消息如何统一处理?
Channel Plugin 架构
每个消息渠道(Telegram/Discord/WhatsApp/Slack)都是一个 Channel Plugin:
src/channels/plugins/index.ts— Plugin 注册中心src/channels/plugins/load.ts— Plugin 动态加载src/channels/plugins/bundled.ts— 内置 Plugin 列表src/channels/plugins/catalog.ts— Plugin 元数据目录
Plugin SDK — 消息标准化
Channel Plugin 使用统一的 SDK 将平台消息转化为内部格式:
src/plugin-sdk/inbound-envelope.ts— 入站消息信封,统一封装不同平台的消息src/plugin-sdk/routing.ts— 路由辅助工具
标准化消息结构 — MsgContext
src/auto-reply/templating.ts#L14—MsgContext类型定义
// 标准化后的消息包含这些关键字段:
type MsgContext = {
Body: string; // 原始消息文本
BodyForAgent: string; // 带时间戳的消息(给 Agent 看)
SessionKey: string; // 会话标识
Provider: string; // 来源渠道(telegram/discord/...)
ChatType: string; // direct / group
SenderId: string; // 发送者 ID
CommandAuthorized: boolean; // 是否有命令执行权限
// ... 更多字段
};
消息去重与防抖
src/auto-reply/inbound-debounce.ts#L51—createInboundDebouncer()防止用户短时间连发导致重复处理src/auto-reply/reply/inbound-dedupe.ts— 入站消息去重
WebChat / Gateway 内部渠道
对于 TUI / Control UI / ACP 等内部渠道,消息通过 Gateway RPC 进入:
src/gateway/server-methods/chat.ts#L1106—chat.sendRPC 方法- 验证参数 → 消毒输入 → 解析附件 → 构建
MsgContext→ 调用dispatchInboundMessage()
- 验证参数 → 消毒输入 → 解析附件 → 构建
💡 你会学到
Plugin 模式:每个渠道都是可插拔的。新增一个消息渠道只需要实现 Plugin 接口,不需要修改核心逻辑。
第 3 站:路由决策 — 谁来处理这条消息?
核心问题:消息到达后,如何决定由哪个 Agent 处理?
消息分发入口
src/auto-reply/dispatch.ts#L35—dispatchInboundMessage()入站消息分发src/auto-reply/dispatch.ts#L56—dispatchInboundMessageWithBufferedDispatcher()带缓冲的分发
Agent 路由解析
-
src/routing/resolve-route.ts#L614—resolveAgentRoute()核心路由函数- 读取
openclaw.json中的bindings配置 - 根据渠道、群组、用户匹配绑定规则
- 返回负责处理的 Agent ID
- 读取
-
src/routing/resolve-route.ts#L91—buildAgentSessionKey()构建会话键
Session Key 体系
src/routing/session-key.ts— Session Key 工具函数src/sessions/session-key-utils.ts— 解析 Agent Session Key
Session Key 格式:agent:{agentId}:{channel}:{chatType}:{chatId}
例如:agent:main:telegram:direct:8572674464
权限与访问控制
src/auto-reply/command-auth.ts— 命令权限检查src/channels/allow-from.ts—allowFrom用户白名单src/channels/allowlist-match.ts— 白名单匹配逻辑src/channels/mention-gating.ts— @提及 门控(群聊中只响应被 @ 的消息)src/auto-reply/group-activation.ts— 群聊激活规则
💡 你会学到
Strategy 模式:不同渠道、不同用户、不同群组可以绑定到不同的 Agent,实现精准的任务分流。路由规则是配置驱动的,不需要改代码。
第 4 站:会话初始化与上下文装配
核心问题:Agent 开始处理前,需要准备哪些上下文?
核心入口
src/auto-reply/reply/get-reply.ts#L57—getReplyFromConfig()
这个函数做了大量幕后工作,但不会调用大模型:
Step 1:确定 Agent 和工作区
src/agents/agent-scope.ts—resolveSessionAgentId()/resolveAgentDir()src/agents/workspace.ts—ensureAgentWorkspace()确保工作目录存在
Step 2:媒体与链接理解
如果消息包含图片、文件或链接,先进行深度解析:
src/media-understanding/apply.ts—applyMediaUnderstanding()图片/文件解析src/link-understanding/apply.ts—applyLinkUnderstanding()URL 内容提取
Step 3:会话状态初始化
src/auto-reply/reply/session.ts#L169—initSessionState()- 加载历史对话记录
- 恢复会话上下文
- 这就是 AI "记住"你之前说过的话的原理 — 不是真正的记忆,而是每次推理前重新加载历史
Step 4:解析控制指令
src/auto-reply/reply/get-reply-directives.ts—resolveReplyDirectives()解析/reset、/model、/think等指令src/auto-reply/reply/get-reply-inline-actions.ts—handleInlineActions()处理不需要 AI 推理就能完成的内置命令
Step 5:Typing 状态
src/auto-reply/reply/typing.ts#L16—createTypingController()在聊天界面显示"正在输入…"
💡 你会学到
到这一步为止,系统还没有调用任何大模型。所有的工作都是在准备上下文——这正是 OpenClaw 区别于简单 API wrapper 的关键。
第 5 站:执行配置与任务排队
核心问题:准备好的上下文如何打包成执行任务?
执行配置构建
src/auto-reply/reply/get-reply-run.ts#L182—runPreparedReply()
这个函数将所有准备好的参数打包:
-
Thinking Level 解析 —
/think high等用户指令会调整推理深度src/auto-reply/thinking.ts—normalizeThinkLevel()/supportsXHighThinking()
-
队列策略
src/auto-reply/reply/queue.ts—resolveQueueSettings()消息排队规则src/auto-reply/reply/queue/enqueue.ts— 入队逻辑src/auto-reply/reply/queue/drain.ts— 出队执行
-
群聊上下文构建
src/auto-reply/reply/groups.ts—buildGroupChatContext()/buildGroupIntro()
-
入站元数据注入
src/auto-reply/reply/inbound-meta.ts—buildInboundMetaSystemPrompt()构建信任元数据
-
路由回复
src/auto-reply/reply/route-reply.ts—routeReply()确定回复路由
最终调用 → runReplyAgent()
💡 你会学到
Pipeline 模式:消息经过一系列 transform 阶段(标准化 → 路由 → 上下文装配 → 执行配置),每个阶段只关注自己的职责。
第 6 站:Agent Runner — 生命周期管理
核心问题:Agent 的执行生命周期是怎么管理的?
核心入口
src/auto-reply/reply/agent-runner.ts#L63—runReplyAgent()
这个函数管理 Agent 的完整生命周期:
Step 1:记忆刷新
src/auto-reply/reply/agent-runner-memory.ts#L250—runMemoryFlushIfNeeded()- 长对话中,当上下文接近窗口上限时,自动压缩历史并持久化到记忆文件
- 这是 长会话记忆机制 的核心
Step 2:Block Streaming 管线
src/auto-reply/reply/block-reply-pipeline.ts#L85—createBlockReplyPipeline()- 模型生成的内容被分成 “block”,逐块流式推送给用户
- 这就是"打字机效果"的实现
Step 3:执行并构建回复
调用 → runAgentTurnWithFallback()
Step 4:构建回复 Payload
src/auto-reply/reply/agent-runner-payloads.ts#L93—buildReplyPayloads()将模型结果整理成可发送格式
Step 5:成本计算与诊断
src/utils/usage-format.ts—estimateUsageCost()计算本次推理的美元成本src/infra/diagnostic-events.ts—emitDiagnosticEvent()上报运行诊断信息
Step 6:Followup 处理
src/auto-reply/reply/followup-runner.ts#L37—createFollowupRunner()- 检查队列中是否有后续消息需要处理
- 如果有,继续处理下一条,形成持续运行循环
💡 你会学到
Observer 模式:Agent 生命周期中的每个阶段都通过事件(emitAgentEvent、emitDiagnosticEvent)通知订阅者,实现松耦合的监控和扩展。
第 7 站:执行层 — Fallback 与容错
核心问题:模型调用失败怎么办?
核心入口
src/auto-reply/reply/agent-runner-execution.ts#L76—runAgentTurnWithFallback()
Step 1:注册运行上下文
const runId = crypto.randomUUID(); // 全局唯一运行标识
registerAgentRunContext(runId, ...); // 注册上下文,用于追溯
src/infra/agent-events.ts—registerAgentRunContext()/emitAgentEvent()
Step 2:CLI vs 嵌入式模式选择
src/agents/cli-runner.ts—runCliAgent()CLI 后端执行器src/agents/model-selection.ts—isCliProvider()判断是否 CLI 模式
Step 3:Model Fallback 机制
src/agents/model-fallback.ts#L511—runWithModelFallback()- 如果主模型调用失败(网络错误、限流、计费问题…)
- 自动按配置的 fallback 链切换到备用模型
- 支持重试策略和冷却期管理
Step 4:Failover 错误分类
src/agents/failover-error.ts—FailoverError/resolveFailoverStatus()src/agents/pi-embedded-helpers.ts— 错误分类函数:isCompactionFailureError()— 上下文压缩失败isContextOverflowError()— 上下文窗口溢出isBillingErrorMessage()— 计费错误isTransientHttpError()— 临时网络错误(可重试)
💡 你会学到
容错设计:OpenClaw 在生产环境中需要处理各种不可预期的失败。Fallback 机制确保单个模型失败不会导致用户得不到回复。
第 8 站:嵌入式运行时 — 模型解析与认证
核心问题:系统如何确定用哪个模型、用哪个 API Key?
核心入口
src/agents/pi-embedded-runner/run.ts#L265—runEmbeddedPiAgent()
Step 1:Lane 排队
src/agents/pi-embedded-runner/lanes.ts—resolveSessionLane()/resolveGlobalLane()- 确定本次调用的排队规则:会话级顺序执行 or 全局统一调度
src/process/command-queue.ts—enqueueCommandInLane()入队执行
Step 2:模型解析
src/agents/pi-embedded-runner/model.ts—resolveModelAsync()补全模型完整信息- 模型名称、上下文窗口、API 地址、调用方式、默认参数
src/agents/model-catalog.ts— 内置模型目录src/agents/model-id-normalization.ts— 模型 ID 标准化
Step 3:API 密钥认证
src/agents/model-auth.ts#L540—getApiKeyForModel()获取模型 API Keysrc/agents/model-auth.ts#L282—resolveApiKeyForProvider()解析 Provider 密钥
多密钥轮询机制:
src/agents/auth-profiles/— Auth Profile 系统src/agents/auth-profiles/order.ts— 密钥优先级排序src/agents/auth-profiles/credential-state.ts— 密钥状态跟踪- 如果当前密钥认证失败 → 自动切换到下一个 → 直到找到可用密钥或全部耗尽
Step 4:上下文窗口保护
src/agents/context-window-guard.ts—evaluateContextWindowGuard()/resolveContextWindowInfo()- 检查上下文是否即将溢出
- 必要时触发自动压缩(compaction)
Step 5:Compaction(上下文压缩)
src/agents/compaction.ts—buildCompactionSummarizationInstructions()/estimateMessagesTokens()src/agents/pi-embedded-runner/compact.ts—compactEmbeddedPiSession()执行压缩
💡 你会学到
多层保护:模型解析 → API 认证 → 上下文窗口检查 → 自动压缩。每一层都有失败处理,确保推理请求在最佳状态下发出。
第 9 站:核心推理 — 真正调用大模型
核心问题:最终是怎么调用大模型的?
核心入口
src/agents/pi-embedded-runner/run/attempt.ts—runEmbeddedAttempt()(约 2900 行,整个系统最复杂的单文件)
Step 1:工作环境准备
// Line 1384
const resolvedWorkspace = resolveUserPath(params.workspaceDir);
// Line 1399
const sandbox = await resolveSandboxContext({ ... });
src/agents/sandbox.ts—resolveSandboxContext()沙箱环境边界
Step 2:工具创建
src/agents/pi-tools.ts#L198—createOpenClawCodingTools()创建 Agent 可用的所有工具
src/agents/openclaw-tools.ts#L30—createOpenClawTools()OpenClaw 专属工具src/agents/bash-tools.ts— exec/process 等命令行工具src/agents/memory-search.ts— memory_search 工具
Step 3:Skill 加载
src/agents/pi-embedded-runner/skills-runtime.ts— 加载当前 Agent 可用的 Skill 文件src/agents/skills/— Skill 系统
Step 4:系统提示词构建
-
src/agents/pi-embedded-runner/system-prompt.ts#L11—buildEmbeddedSystemPrompt()- 注入所有运行时信息到系统提示词:
- Agent 配置、技能文档、项目文件
- 运行时环境(OS、时区、模型信息)
- 渠道能力(支持 Markdown?支持按钮?)
- 记忆文件(MEMORY.md、日志)
- 注入所有运行时信息到系统提示词:
-
src/agents/pi-embedded-runner/system-prompt.ts#L96—applySystemPromptOverrideToSession()将提示词固定到会话 -
src/agents/pi-embedded-runner/run/attempt.ts#L1231—composeSystemPromptWithHookContext()合并 Hook 注入的上下文
⚠️ 双刃剑:系统提示词包含的信息越多,模型的环境理解越完整,但 token 消耗也越大。这是 OpenClaw token 消耗较快的核心原因之一。
Step 5:创建 Agent Session(Pi SDK)
// Line 1854
({ session } = await createAgentSession({
model,
tools,
systemPrompt,
// ...
}));
- 使用
@mariozechner/pi-coding-agent的createAgentSession() - 绑定所有工具、上下文、规则到这个会话
Step 6:Stream Function 创建
不同模型 Provider 使用不同的流式调用函数:
src/agents/pi-embedded-runner/anthropic-stream-wrappers.ts— Anthropic Claudesrc/agents/pi-embedded-runner/openai-stream-wrappers.ts— OpenAI GPTsrc/agents/pi-embedded-runner/moonshot-stream-wrappers.ts— Moonshot/Kimisrc/agents/pi-embedded-runner/zai-stream-wrappers.ts— z.aisrc/agents/pi-embedded-runner/proxy-stream-wrappers.ts— 代理模式src/agents/ollama-stream.ts— Ollama 本地模型
Step 7:发起推理请求!🚀
// Line 2539-2541
await activeSession.prompt(effectivePrompt, { images: imageResult.images });
// 或
await activeSession.prompt(effectivePrompt);
这是整个链路中,真正调用大模型的唯一一行代码。
Step 8:Agent Loop(由 Pi SDK 管理)
prompt() 内部运行 Agent Loop:
- 模型生成文本 / 工具调用
- 如果触发工具调用 → 执行工具 → 结果写回历史 → 继续推理
- 循环直到模型认为任务完成
Step 9:事件订阅与流式输出
src/agents/pi-embedded-subscribe.ts#L34—subscribeEmbeddedPiSession()- 订阅模型输出事件
onPartialReply/onBlockReply回调- 逐段将模型输出推送到前端
💡 你会学到
核心洞察:OpenClaw 本身不生产智能——它把推理任务完全交给 Pi SDK + 大模型。OpenClaw 的价值在于构建了一套完整的运行时装配体系,让每次推理都在最佳上下文中执行。
第 10 站:回复分发 — 消息送达用户
核心问题:模型的回复如何送回用户的聊天窗口?
回复分发管线
src/auto-reply/reply/reply-dispatcher.ts#L113—createReplyDispatcher()创建回复分发器src/auto-reply/reply/reply-delivery.ts#L63—createBlockReplyDeliveryHandler()Block 级回复递送
流式分发流程
回复格式适配
src/auto-reply/reply/normalize-reply.ts— 回复内容标准化src/auto-reply/reply/reply-tags.ts— 解析[[reply_to_current]]等标签src/auto-reply/reply/reply-media-paths.ts— 媒体路径处理
平台特定处理
不同平台有不同的消息能力和限制:
src/auto-reply/chunk.ts— 长消息分块src/auto-reply/reply/block-streaming.ts— 流式输出配置src/auto-reply/reply/session-delivery.ts— 会话级递送
会话状态持久化
回复发送后,系统更新会话状态:
💡 你会学到
回复分发不是简单的"把文字发回去"。系统需要处理流式输出、格式适配、长消息分块、平台限制等大量边缘情况。
核心子系统
🧠 记忆系统
src/memory/index.ts— 记忆系统入口src/memory/manager.ts—MemoryManager核心管理器src/memory/search-manager.ts— 语义搜索管理src/memory/embeddings.ts— 向量嵌入src/memory/embeddings-gemini.ts— Gemini Embeddingsrc/memory/embeddings-openai.ts— OpenAI Embeddingsrc/memory/sqlite.ts— SQLite 存储后端src/memory/multimodal.ts— 多模态索引(图片/音频)
⏰ Cron 定时任务
src/cron/service.ts— Cron 服务核心src/cron/isolated-agent.ts— 隔离 Agent 执行src/cron/isolated-agent/run.ts— 执行逻辑src/cron/schedule.ts— 调度器src/cron/delivery.ts— 结果递送
🌐 浏览器控制
src/browser/cdp.ts— Chrome DevTools Protocolsrc/browser/chrome.ts— Chrome 浏览器管理src/browser/chrome-mcp.ts— Chrome DevTools MCP 模式src/browser/bridge-server.ts— 浏览器桥接服务器
🔌 Plugin 系统
src/plugins/runtime/— Plugin 运行时src/plugin-sdk/— Plugin SDKsrc/plugins/contracts/— Plugin 接口契约
🔐 安全系统
src/security/— 安全审计与检查src/security/external-content.ts— 外部内容边界标记src/security/audit.ts— 安全审计src/infra/system-run-approval-binding.ts— 命令执行审批绑定
🪝 Hook 系统
src/hooks/hooks.ts— Hook 引擎src/hooks/loader.ts— Hook 加载器src/hooks/bundled/session-memory/handler.ts— 会话记忆 Hooksrc/hooks/bundled/boot-md/handler.ts— BOOT.md Hook
🤖 ACP(Agent Communication Protocol)
src/acp/server.ts— ACP 服务器src/acp/client.ts— ACP 客户端src/acp/session.ts— ACP 会话管理src/acp/control-plane/manager.ts— ACP 控制平面src/acp/control-plane/spawn.ts— ACP 会话创建
🗣️ TTS 语音合成
src/tts/tts.ts— TTS 核心逻辑src/tts/providers/elevenlabs.ts— ElevenLabssrc/tts/providers/openai.ts— OpenAI TTSsrc/tts/providers/microsoft.ts— Microsoft TTS
🔑 Secrets 管理
src/secrets/resolve.ts— Secret 解析src/secrets/runtime.ts— 运行时 Secret 管理src/secrets/audit.ts— Secret 审计
设计模式总结
| 模式 | 在哪里 | 关键文件 |
|---|---|---|
| Plugin/Provider | 渠道接入、模型 Provider、TTS Provider | src/channels/plugins/ / src/providers/ |
| Pipeline/Middleware | 消息处理链 | src/auto-reply/dispatch.ts → get-reply → agent-runner |
| Observer/Event | 生命周期事件、Hook 系统 | src/infra/agent-events.ts / src/hooks/ |
| Strategy | 模型选择、认证策略、Fallback | src/agents/model-fallback.ts / src/agents/model-auth.ts |
| Factory | Session/Agent/Tool 创建 | src/agents/pi-tools.ts / src/auto-reply/reply/session.ts |
| Queue/Lane | 任务排队与并发控制 | src/process/command-queue.ts / src/agents/pi-embedded-runner/lanes.ts |
| Chain of Responsibility | Fallback 降级链 | src/agents/model-fallback.ts / src/agents/auth-profiles/order.ts |
关键洞察
1. OpenClaw 是一个运行时装配引擎
它的核心价值不是 AI 推理本身,而是:
- 将用户消息精准嵌入到全维度运行环境中
- 管理认证、工具、上下文、会话状态的完整生命周期
2. 智能生成完全委托给 Pi SDK
OpenClaw 做了所有的"脏活累活"——鉴权、路由、工具管理、上下文装配、异常处理——然后把整理好的数据交给 @mariozechner/pi-coding-agent 的 createAgentSession().prompt() 完成推理。
3. 提示词工程做到了极致
所有运行时信息都会结构化地注入系统提示词——这既是优势(模型获得完整环境理解),也是代价(token 消耗高、注意力稀释)。
4. 本质是一个本地优先的网关系统
5. 从代码量看优先级
| 模块 | 文件数 | 核心关注 |
|---|---|---|
agents/ |
200+ | 模型管理、工具、认证、嵌入式运行时 |
auto-reply/ |
170+ | 消息处理管线、命令系统、回复分发 |
gateway/ |
180+ | Gateway 服务器、RPC、认证、Control UI |
channels/ |
50+ | 渠道 Plugin、平台适配 |
memory/ |
60+ | 向量搜索、嵌入、索引 |
security/ |
20+ | 安全审计、命令审批 |
推荐阅读顺序
- 先读
src/auto-reply/dispatch.ts— 消息分发入口,理解全局流程 - 然后
src/auto-reply/reply/get-reply.ts— 上下文装配 - 然后
src/auto-reply/reply/agent-runner.ts— Agent 生命周期 - 然后
src/agents/pi-embedded-runner/run.ts— 嵌入式运行时 - 最后
src/agents/pi-embedded-runner/run/attempt.ts— 核心推理(最复杂) - 按兴趣 深入各子系统(memory/、cron/、browser/、acp/)
Generated from OpenClaw source at /Users/GitRepos/openclaw — 2026-03-17
AtomGit 是由开放原子开源基金会联合 CSDN 等生态伙伴共同推出的新一代开源与人工智能协作平台。平台坚持“开放、中立、公益”的理念,把代码托管、模型共享、数据集托管、智能体开发体验和算力服务整合在一起,为开发者提供从开发、训练到部署的一站式体验。
更多推荐

所有评论(0)