主题
Chrome 扩展核心架构
本文引用的源码文件
本文引用的文件
目录
引言
本文件面向 Chrome 扩展 MV3 的核心架构,聚焦 Service Worker 生命周期、保活策略、Offscreen Document 剪贴板能力、四个核心上下文(Background Service Worker、Side Panel、Content Scripts、Offscreen Document)的职责划分与通信协议。文档同时给出消息路由表设计、事件驱动架构、状态同步机制、安全沙箱限制及绕过方案,并配套架构图、时序图与流程图,帮助读者从高层到代码级全面理解该扩展的运行模型。
项目结构
扩展采用双进程架构:Chrome 扩展端(Manifest V3,Service Worker + Side Panel + Content Script + Offscreen Document)与独立本地代理端 Agent(Node.js)。扩展入口由 manifest.json 声明,Background Service Worker 负责调度、保活、侧边栏控制、工具执行和与 Agent 的 HTTP/WebSocket 通信;Side Panel 提供用户界面;Content Script 在页面上下文中执行页面读取与交互;Offscreen Document 用于访问系统剪贴板等受限 API。
graph TB A["manifest.json<br/>声明 MV3 扩展"] --> B["Background Service Worker<br/>src/background/index.js"] B --> C["Side Panel UI<br/>src/side_panel/index.js"] B --> D["Content Scripts<br/>src/content/index.js"] B --> E["Offscreen Document<br/>src/offscreen/offscreen.html/js"] B --> F["本地 Agent 客户端<br/>src/background/local-agent-client.js"] F --> G["Agent 服务<br/>HTTP/WebSocket 接口"]
图表来源
- manifest.json#L1-L76
- src/background/index.js#L1-L120
- src/offscreen/offscreen.html#L1-L12
- src/offscreen/offscreen.js#L1-L68
- src/content/index.js#L1-L60
- src/background/local-agent-client.js#L40-L94
章节来源
核心组件
- Background Service Worker:扩展中枢,负责 ReAct 执行循环、任务续跑、侧边栏开关/分组、keepalive 长连接、消息分发、工具执行编排、与 Agent 通信。
- Side Panel:用户交互主界面,负责会话管理、提示词、工具面板、截图、工作区、记忆配置等。
- Content Scripts:注入目标页面,提供页面文本/HTML 提取、元素交互、表单操作、截图区域选择等。
- Offscreen Document:承载剪贴板读写能力,绕过 Service Worker 的沙箱限制。
- Agent 客户端:封装与本地 Agent 的 HTTP/WebSocket 调用,包括文件、命令、MCP、Skill、RAG 等能力。
章节来源
- src/background/index.js#L1-L120
- src/side_panel/index.js#L1-L60
- src/content/index.js#L1-L60
- src/offscreen/offscreen.js#L1-L68
- src/background/local-agent-client.js#L40-L94
架构总览
MV3 Service Worker 的生命周期由浏览器管理,空闲时可能被终止。扩展通过以下机制保证关键任务不中断:
- keepalive 长连接:Side Panel 通过 chrome.runtime.connect 建立命名端口,防止 SW 被判定为空闲。
- 闹钟续跑:使用 chrome.alarms 注册周期闹钟,SW 被回收后由闹钟唤醒,扫描 checkpoint 自动恢复执行。
- Offscreen Document:按需创建,提供剪贴板读写能力,避免在 SW 中直接调用受限 API。
sequenceDiagram participant SP as "Side Panel" participant BG as "Background Service Worker" participant OS as "Offscreen Document" participant CS as "Content Script" participant AG as "Agent 服务" SP->>BG : 建立 keepalive 长连接 BG-->>SP : 确认连接/身份上报 SP->>BG : 发起任务/CALL_API BG->>OS : 确保 Offscreen 文档存在 OS-->>BG : 剪贴板结果 BG->>CS : 发送页面读取/交互消息 CS-->>BG : 页面数据/交互结果 BG->>AG : HTTP/WebSocket 调用 AG-->>BG : 流式/非流式响应 BG-->>SP : 进度/完成/错误通知
图表来源
- src/background/index.js#L140-L218
- src/background/auto-resume.js#L61-L112
- src/background/tool-executor.js#L4885-L4912
- src/offscreen/offscreen.js#L18-L67
- src/content/index.js#L74-L193
- src/background/local-agent-client.js#L399-L443
详细组件分析
Background Service Worker 生命周期与保活
- 启动阶段:初始化 i18n、重建定时任务闹钟、清理过期 ReAct checkpoint、迁移旧格式 Agent 数据。
- 保活机制:Side Panel 通过命名端口 keepalive-<sessionId> 建立长连接,SW 维护连接注册表,支持实例定向消息。
- 自动续跑:主任务期间注册 30s 周期闹钟;SW 被回收后闹钟触发,扫描 checkpoint 决定是否续跑,最多尝试 N 次,超限后静默防风暴。
- 面板控制:根据全局或 per-tab 模式打开/关闭侧边栏,维护窗口/标签页映射,处理快捷键切换。
flowchart TD
Start(["Service Worker 启动"]) --> Init["初始化 i18n/闹钟/Checkpoint 清理"]
Init --> Keepalive["监听 keepalive 端口"]
Keepalive --> Watch{"是否已有活跃任务?"}
Watch -- 否 --> Idle["等待事件/保持存活"]
Watch -- 是 --> Alarm["注册 30s 闹钟"]
Alarm --> Resume{"SW 被回收后闹钟触发"}
Resume --> Decide["决策是否需要续跑"]
Decide -- 需要 --> Restore["恢复 checkpoint 继续执行"]
Decide -- 不需要 --> End(["结束/等待下次事件"])
图表来源
- src/background/index.js#L56-L95
- src/background/index.js#L140-L218
- src/background/auto-resume.js#L61-L112
章节来源
Side Panel 职责与状态同步
- 职责:会话管理、提示词、工具面板、截图、工作区、记忆配置、Agent 配对与状态展示。
- 状态同步:监听 storage 变更实时更新 UI;与 Background 通过 chrome.runtime.sendMessage 和 keepalive 端口进行双向通信;处理 SW 重启事件并提示用户继续执行。
- 可见性判定:基于 keepalive 上报的 windowId/hostTabId 判断“发起实例面板是否可见”,决定桌面通知策略。
classDiagram
class SidePanel {
+会话管理()
+提示词管理()
+工具面板()
+截图与预览()
+工作区管理()
+记忆配置()
+Agent 配对与状态()
}
class BackgroundState {
+keepalivePorts Map
+keepaliveIdentities Map
+activeReactLoops Set
+cancelReactLoop()
+getKeepalivePort()
}
SidePanel --> BackgroundState : "消息/端口通信"
图表来源
章节来源
Content Scripts 消息路由表
- 路由表:HANDLERS Map 将 message.type 映射到具体处理器,O(1) 查找。
- 异步处理:ASYNC_HANDLERS Set 标记需 return true 保持通道开放的异步工具。
- 顶层帧保护:TOP_FRAME_ONLY_TYPES 限定某些工具仅在顶层 frame 响应,避免 iframe 覆盖。
- 功能分类:页面读取、页面交互、表单输入、信息提取、媒体输出、异步工具、区域截图选择、页面度量。
flowchart TD
In(["收到消息"]) --> CheckTop{"是否顶层帧必需?"}
CheckTop -- 是且非顶层 --> Drop["忽略消息"]
CheckTop -- 否或顶层 --> Lookup["HANDLERS 查找处理器"]
Lookup --> Found{"找到处理器?"}
Found -- 否 --> Exit["退出"]
Found -- 是 --> Exec["执行处理器"]
Exec --> Async{"是否异步?"}
Async -- 是 --> Hold["return true 保持通道"]
Async -- 否 --> Reply["sendResponse 同步返回"]
图表来源
章节来源
Offscreen Document 剪贴板能力
- 目的:绕过 Service Worker 沙箱对剪贴板的限制,提供安全的剪贴板读写能力。
- 实现:按需创建 Offscreen Document,监听 runtime.onMessage,处理 COPY_TO_CLIPBOARD 与 PASTE_FROM_CLIPBOARD,失败时回退到 textarea.execCommand。
- 资源管理:ensureOffscreenDocument 去重创建,避免重复实例。
sequenceDiagram
participant BG as "Background"
participant OS as "Offscreen Document"
BG->>OS : ensureOffscreenDocument()
OS-->>BG : 文档就绪
BG->>OS : sendMessage(COPY_TO_CLIPBOARD/PASTE_FROM_CLIPBOARD)
OS-->>BG : sendResponse({success, message/text/error})
图表来源
章节来源
- src/offscreen/offscreen.html#L1-L12
- src/offscreen/offscreen.js#L1-L68
- src/background/tool-executor.js#L4885-L5049
与 Agent 的通信契约
- 认证:Bearer Token,所有请求携带 Authorization 头。
- 接口:文件系统、命令执行、MCP 工具、Skill、RAG 知识库等。
- 超时与取消:AbortController 统一超时控制,区分 AbortError 与其他网络错误。
- 可达性缓存:按 agentId 缓存可达性,不可达时快速失败,避免阻塞。
sequenceDiagram participant BG as "Background" participant AC as "AgentClient" participant AG as "Agent 服务" BG->>AC : agentRequest(path, body, method, timeout) AC->>AG : HTTP 请求 (Authorization : Bearer token) AG-->>AC : JSON 响应 AC-->>BG : 附加 httpStatus 的结果
图表来源
章节来源
依赖关系分析
- Background Service Worker 依赖 state.js 管理会话取消、AbortController、keepalive 端口与实例身份。
- tool-executor.js 作为工具执行中枢,依赖 local-agent-client.js 与 Agent 通信,依赖 content script 进行页面操作,依赖 offscreen document 进行剪贴板操作。
- auto-resume.js 仅依赖 logger,通过回调注入 background/index.js,避免反向依赖。
- side_panel/index.js 依赖 shared 模块(主题、i18n、token 计数等),并通过 runtime 消息与 Background 通信。
graph LR BG["background/index.js"] --> ST["background/state.js"] BG --> AE["background/auto-resume.js"] BG --> TE["background/tool-executor.js"] TE --> LAC["background/local-agent-client.js"] TE --> OFF["offscreen/offscreen.js"] BG --> CS["content/index.js"] SP["side_panel/index.js"] --> BG
图表来源
- src/background/index.js#L1-L20
- src/background/tool-executor.js#L1-L23
- src/background/local-agent-client.js#L1-L4
- src/offscreen/offscreen.js#L1-L2
- src/content/index.js#L1-L34
- src/side_panel/index.js#L1-L34
章节来源
- src/background/index.js#L1-L120
- src/background/tool-executor.js#L1-L23
- src/background/local-agent-client.js#L1-L4
- src/offscreen/offscreen.js#L1-L2
- src/content/index.js#L1-L34
- src/side_panel/index.js#L1-L34
性能与内存优化
- Service Worker 保活:通过 keepalive 端口维持长连接,避免频繁重建;闹钟续跑减少任务丢失风险。
- 消息体积控制:日志截断策略保留关键子任务计划条目,避免历史视图缺失。
- 工具执行优化:AbortController 统一超时控制,避免长时间阻塞;可达性缓存快速失败离线 Agent。
- Offscreen Document 复用:ensureOffscreenDocument 去重创建,避免重复实例开销。
- Content Script 路由:Map 查找 O(1),异步工具集合明确标识,减少不必要的通道保持。
- 存储与状态:按 sessionId 隔离状态,派生会话祖先链回退,避免多实例广播误判。
[本节为通用指导,无需特定文件引用]
故障排查指南
- Service Worker 被回收导致任务中断:检查闹钟续跑逻辑与 checkpoint 是否有效;查看自动续跑尝试次数是否耗尽。
- Side Panel 无法打开或关不掉:检查手势上下文、per-tab 启用状态、onOpened/onClosed 事件映射;确认 close() 兼容版本分支。
- 剪贴板读写失败:确认 Offscreen Document 已创建;检查 COPY_TO_CLIPBOARD/PASTE_FROM_CLIPBOARD 消息是否正确;查看回退路径 execCommand 是否成功。
- Content Script 无响应:确认 TOP_FRAME_ONLY_TYPES 限制;检查 ASYNC_HANDLERS 是否包含对应类型;验证 isExtensionValid 校验。
- Agent 不可达:检查 pairedAgents 配置与 activeAgentId;查看可达性缓存;确认 Bearer Token 与网络权限。
章节来源
- src/background/auto-resume.js#L39-L55
- src/background/index.js#L682-L747
- src/offscreen/offscreen.js#L18-L67
- src/content/index.js#L195-L247
- src/background/local-agent-client.js#L100-L140
结论
该扩展以 MV3 Service Worker 为核心,结合 Side Panel、Content Scripts 与 Offscreen Document 形成清晰的上下文分工。通过 keepalive 长连接与闹钟续跑保障任务连续性,通过消息路由表与事件驱动架构实现高效通信,通过 Offscreen Document 绕过剪贴板限制。Agent 客户端统一封装 HTTP/WebSocket 调用,配合可达性缓存与超时控制提升稳定性。整体架构兼顾安全性、可维护性与用户体验,适合复杂自动化与 AI 辅助场景。