【Eigent 源码架构与实战】开源 Cowork 桌面、多智能体 Workforce、Trigger 自动化与本地部署

Eigent 开源 Cowork 桌面技术全景

  • [一、产品定位与效果:从对话助手走向 Agentic Workspace](#一、产品定位与效果:从对话助手走向 Agentic Workspace)
    • [1.1 Eigent 解决的是"让 Agent 在项目上下文中完成工作"](#1.1 Eigent 解决的是“让 Agent 在项目上下文中完成工作”)
    • [1.2 Single Agent 与 Workforce 不是同一个界面的两种皮肤](#1.2 Single Agent 与 Workforce 不是同一个界面的两种皮肤)
  • [二、系统架构与核心数据流:桌面端、Brain 与本地服务如何协作](#二、系统架构与核心数据流:桌面端、Brain 与本地服务如何协作)
    • [2.1 技术分层、运行拓扑与源码目录](#2.1 技术分层、运行拓扑与源码目录)
    • [2.2 一次任务从 `/chat` 到桌面事件与固定工作目录](#2.2 一次任务从 /chat 到桌面事件与固定工作目录)
    • [2.3 Trigger:Celery 负责调度,在线桌面负责真正执行 Agent](#2.3 Trigger:Celery 负责调度,在线桌面负责真正执行 Agent)
  • [三、Agent 与 Workforce 内核:规划、分配、执行、失败和记忆](#三、Agent 与 Workforce 内核:规划、分配、执行、失败和记忆)
    • [3.1 Workforce:Eigent 包装 CAMEL,而不是重写一套调度器](#3.1 Workforce:Eigent 包装 CAMEL,而不是重写一套调度器)
    • [3.2 Single Agent:跳过 Workforce,但仍然是带工具的执行器](#3.2 Single Agent:跳过 Workforce,但仍然是带工具的执行器)
    • [3.3 Remote Sub Agent:受策略约束的委派工具,不自动继承本地工作区](#3.3 Remote Sub Agent:受策略约束的委派工具,不自动继承本地工作区)
    • [3.4 项目记忆是本地结构化上下文,不是默认向量 RAG](#3.4 项目记忆是本地结构化上下文,不是默认向量 RAG)
  • [四、模型、工具、MCP 与安全边界:Agent 到底能做什么](#四、模型、工具、MCP 与安全边界:Agent 到底能做什么)
    • [4.1 模型层统一了入口,没有抹平模型差异](#4.1 模型层统一了入口,没有抹平模型差异)
    • [4.2 工具暴露分为预置 Toolkit、MCP、Skills 和人工交互](#4.2 工具暴露分为预置 Toolkit、MCP、Skills 和人工交互)
    • [4.3 Hands/Sandbox 与两套后端的认证边界](#4.3 Hands/Sandbox 与两套后端的认证边界)
  • 五、安装与部署:从快速体验到完全本地
    • [5.1 从源码启动桌面端:默认连接 Eigent 云服务](#5.1 从源码启动桌面端:默认连接 Eigent 云服务)
    • [5.2 完全本地:先启动控制面,再让桌面指向它](#5.2 完全本地:先启动控制面,再让桌面指向它)
    • [5.3 跑通第一个可验证任务](#5.3 跑通第一个可验证任务)
    • [5.4 生产前必须改掉示例配置](#5.4 生产前必须改掉示例配置)
  • 六、工程边界、适用场景与落地建议
    • [6.1 运行状态、认证、数据出网与并发边界](#6.1 运行状态、认证、数据出网与并发边界)
    • [6.2 适用场景与落地顺序](#6.2 适用场景与落地顺序)
  • 参考资料

Eigent 是一个开源 Cowork 桌面应用,将项目文件、模型、浏览器、终端、MCP 与 Skills 组织进可持续工作的 Agentic Workspace,把"选择工作目录---理解上下文---拆分任务---分配专业 Agent---调用浏览器/终端/文件/MCP---产出文件---继续下一轮"放进桌面工作台。本文基于固定提交,拆解 Single Agent 与 Workforce、CAMEL 调度、Trigger 桌面执行链、Remote Sub Agent、工具暴露、本地记忆和双后端部署,并说明"无人值守""本地运行"和"沙箱"的真实边界。
GitHub仓库:https://github.com/cmyk-labs/eigent.git

(如果这个仓库对你有帮助,欢迎在 GitHub 上点一个 Star ⭐ 支持一下。)

官方GitHub仓库:https://github.com/eigent-ai/eigent

官方文档:https://www.eigent.ai/docs/

一、产品定位与效果:从对话助手走向 Agentic Workspace

1.1 Eigent 解决的是"让 Agent 在项目上下文中完成工作"

传统对话产品的上下文主要来自当前聊天;Eigent 则要求先选择 Space 或本地项目目录,让文件、运行记录、产物和工具成为任务的一部分。一次较完整的工作过程可以概括为:

text 复制代码
选择本地文件夹或空白 Space
  → 创建 Project 与本次 Run
  → 输入目标、添加附件、选择执行模式
  → Single Agent 直接执行,或 Workforce 先规划任务
  → Agent 使用文件、终端、浏览器、搜索、MCP、Skills
  → 桌面端实时展示任务、工具调用、终端和产物
  → 结果与项目上下文留给后续 Run 使用

围绕这条链路,Eigent 当前主要包含以下能力:

功能域 用户看到的能力 源码中的主要承载层
工作空间 Space、本地文件夹、Project、Run、附件与输出文件 React/Electron、workspace_resolver.py、Space overlay
执行模式 Single Agent 与多智能体 Workforce single_agent_service.pychat_service.py、CAMEL Workforce
专业角色 Developer、Browser、Document、Multi-Modal、自定义 Worker backend/app/agent/factory/
工具扩展 文件、终端、浏览器、搜索、MCP、Skills、人工问询 Eigent Toolkit 包装层与 CAMEL Toolkits
模型 Eigent Cloud、BYOK、OpenAI 兼容接口与本地模型 CAMEL ModelFactory、Provider 配置
自动化 定时任务、Webhook/Slack 等触发入口 server/、Celery Worker/Beat、Trigger 服务
连续上下文 项目级对话、摘要、事实、产物与 Run 状态 ~/.eigent/memory、PostgreSQL 聊天元数据

这里有两个需要先说清的边界。第一,开源桌面、云服务和企业功能不是同一个部署面;例如 SSO、组织级访问控制和定制能力不能因为官网提到 Enterprise 就视为社区源码的默认能力。第二,"本地部署"表示应用、工作区和自建服务可以运行在自己的环境中,不代表数据必然不出网:只要使用云模型、远程 MCP、搜索服务或其他 Connector,相应请求仍会发往外部服务。

1.2 Single Agent 与 Workforce 不是同一个界面的两种皮肤

两种模式共享模型与工具底座,但执行路径不同:

对比项 Single Agent Workforce
适合任务 目标集中、连续迭代、协调成本不值得 多步骤、多专业角色、可并行子任务
规划阶段 不创建 Workforce 任务树 规划器先分解,前端展示并允许调整任务
执行主体 一个 CAMEL Agent 协调器、任务规划器和多个 Worker Node
上下文特点 同一 Agent 延续当前 Project 的多轮上下文 协调器持有规划视图,具体任务交给不同 Worker
工具 文件、浏览器、终端、Skills、MCP 等 每个预置或自定义 Worker 获得自己的工具集合
代价 路径短、模型调用较少 规划、分配、执行、检查与汇总会增加 Token 和时延

图片来源:Eigent 官方 Workforce 文档

因此,简单文件修改不需要为了"多智能体"而强行拆分;研究、编码、资料整理和报告生成能够形成相对独立的工作包时,Workforce 才更有价值。并行不是目标本身,可验证的任务边界和清晰依赖关系才是。

二、系统架构与核心数据流:桌面端、Brain 与本地服务如何协作

2.1 技术分层、运行拓扑与源码目录

Eigent 仓库不是单一 Web 服务,而是由三个自有层组成:

text 复制代码
React + TypeScript UI
  └─ Electron 主进程:桌面窗口、更新、文件/终端桥接、启动 Brain
       └─ backend/ Brain:FastAPI + Uvicorn,端口默认从 5001~5050 选择
            ├─ 任务会话、Workforce/Single Agent、工具、浏览器、工作区、本地记忆
            └─ CAMEL + 模型 API + MCP Server + 本机终端/浏览器

server/ 本地控制面:FastAPI + PostgreSQL + Redis + Celery
  ├─ 用户、Provider、配置、聊天历史、MCP 管理
  └─ 定时/事件触发和远程控制相关服务
层次 主要实现 关键职责
渲染层 React、TypeScript、src/ 项目、任务树、Agent 活动、终端和产物预览
桌面宿主层 Electron Main/Preload 窗口与 IPC、Brain 生命周期、文件和 CDP 浏览器资源
Brain 执行层 FastAPI、CAMEL、backend/app Run 状态、Single Agent/Workforce、工具、记忆与流式事件
本地控制面 server/、PostgreSQL、Redis、Celery 用户、模型/MCP 配置、Space、历史和 Trigger 调度
外部能力 模型 API、MCP Server、Connector、本机浏览器与终端 提供 Eigent 自身之外的推理和业务操作能力
构建交付层 npm、uv、Electron Builder、Docker Compose 管理两套 Python 环境、桌面打包和控制面部署
text 复制代码
eigent/
├── src/                              # React/TypeScript 渲染进程
│   ├── components/                   # 页面与执行过程组件
│   ├── hooks/                        # Trigger 等桌面桥接逻辑
│   ├── service/                      # 前端服务调用
│   └── store/                        # 项目、任务与界面状态
├── electron/
│   ├── main/                         # 窗口、IPC、Brain 与浏览器进程管理
│   └── preload/                      # 受控 Electron API 暴露
├── backend/
│   ├── main.py                       # Brain 启动入口
│   └── app/
│       ├── agent/                    # Agent 工厂与 Toolkit
│       ├── hands/                    # 部署能力探测与资源门控
│       ├── memory/                   # 本地项目记忆
│       ├── remote_sub_agent/         # 远端 Agent Provider 与会话
│       └── run_context/              # Run 工作目录与状态快照
├── server/
│   ├── app/domains/                  # 用户、模型、MCP、Space、Trigger 等领域
│   └── docker-compose.yml            # PostgreSQL、Redis、API、Worker 与 Beat
├── package.json                      # 桌面端依赖与脚本
├── electron-builder.json             # 桌面打包配置
└── LICENSE                           # Apache-2.0 许可证文件

这套目录说明了为什么"完全本地"不等于只启动一个后端:Electron 管理宿主资源,Brain 承担实时 Agent 执行,server/ 保存账户、配置并调度自动任务。三者可以协作,但运行状态、认证方式和扩展边界并不相同。

Electron 在开发和桌面运行时启动 backend/main.py 的 Uvicorn,并把实际 Brain 端口通知渲染进程。Brain 才是一次 Agent 任务的执行引擎;server/ 更像本地账户、配置、历史与自动化控制面。完全本地部署需要同时理解这两套后端,不能只启动 PostgreSQL 容器就认为 Agent 执行链已经就绪。

外部依赖也必须与 Eigent 自有代码分开:

  • 多智能体核心 BaseWorkforceTaskChannel、Agent、模型工厂和大量基础 Toolkit 来自 CAMEL;Brain 依赖固定为 camel-ai[eigent]==0.2.91a5
  • Eigent 自己实现了桌面交互、任务锁与 SSE 协议、Agent 工厂、工具事件包装、能力门控、浏览器资源池、工作目录、Space overlay、本地 Project 记忆和控制面集成。
  • 云模型、本地 OpenAI 兼容推理服务、远程 MCP 及第三方 Connector 是外部系统,其内部限流、权限、可用性和数据策略不由 Eigent 源码保证。

图片来源:Eigent 官方 Workforce 文档

这张图只描述 Brain 内部由 CAMEL 提供的 Workforce 子系统,不包含 Electron 宿主、Brain API、server/ 控制面以及外部模型和 Connector;全系统关系应以上面的运行拓扑和源码目录为准。

2.2 一次任务从 /chat 到桌面事件与固定工作目录

前端向 Brain 的 POST /chat 发送 Chat 配置,其中包含 Project/Task/Run、问题、附件、执行模式、模型平台、模型名称、API 地址、MCP、CDP 浏览器和工作区信息。后端并不是在这个请求函数内一直同步执行,而是先冻结本次 Run 的目录和上下文,再把动作送进任务队列:

text 复制代码
POST /chat
  → get_or_create_task_lock(project_id)
  → freeze_task_directories() 固定工作目录、产物目录和快照
  → 准备 CDP 浏览器与 RunContext
  → MemoryService.on_run_start() 记录用户问题和 Run 状态
  → ActionImproveData 进入 asyncio.Queue
  → step_solve() 消费动作并执行
  → create_agent / task_state / terminal / write_file / ask / end 等事件
  → StreamingResponse(text/event-stream)
  → React 状态仓库更新任务树、Agent、工具活动和预览区

TaskLock 是这条链的会话枢纽:它保存动作队列、人工回复等待者、后台任务、当前状态、RunContext、工作目录、当前进程内的会话历史和 Agent 内存快照。暂停、恢复、停止、增加 Worker、编辑任务和人工回复并不是另起一套 RPC,而是转成不同 Action 写入同一队列。SSE 负责"及时看到发生了什么",不等于任务本身成为无状态请求。

这种设计很适合单机桌面,但也带来扩展边界:当前运行中的 task_locksasyncio.Queue 位于 Brain 进程内。源码没有展示把执行状态放入 Redis 或跨 Brain 进程协调的完整实现。因此不能仅凭 Uvicorn/FastAPI 就宣称可以无状态横向扩展;如果自行部署多个 Brain Worker,需要额外设计会话粘性、任务状态外置和浏览器/终端资源归属。

启动 Run 时,workspace_resolver 会根据 Space、Project 与 workdir_mode 决定实际工作目录。当前模型包含 worktreecopydirect-writeartifact-only 等模式;随后把源目录、任务输出目录、快照和绑定来源冻结到 RunContext。工具写入时,FileToolkit 还会把落在工作目录内的变更登记到 Space overlay,以便后续审阅或应用。

这比让所有 Agent 直接在用户原目录随意修改更容易追踪,但不是所有模式都天然安全:direct-write 就意味着直接修改源目录;终端命令也可能绕过高层文件写入包装。对重要仓库,应先提交或备份现有修改,优先使用隔离工作目录,确认产物后再合并。

2.3 Trigger:Celery 负责调度,在线桌面负责真正执行 Agent

官方的 v0.0.86 发布说明展示了定时与外部事件触发能力,Slack → Odoo CRM 示例则展示了实际业务效果。不过,从固定提交源码看,开源版 Trigger 不是一套完全在服务器后台运行的 Agent Worker,而是"控制面调度 + Redis 事件投递 + 桌面端执行"的组合:

text 复制代码
Celery Beat
  → poll_trigger_schedules 扫描到期 Cron
  → PostgreSQL 创建 pending TriggerExecution
  → Redis Pub/Sub 发布 execution_created
  → 在线桌面的 WebSocket 收到事件并立即 ACK
  → useTriggerTaskExecutor 将任务写入目标 Project 的 queuedMessages
  → useBackgroundTaskProcessor 调用 startTask
  → 本地 Brain 走正常 /chat + SSE + Agent/Workforce 执行链
  → 桌面端把 running / completed / failed 回写控制面

trigger_schedule_task.py中的 Celery 任务负责轮询到期计划和检查超时;trigger_schedule_service.py创建执行记录、推进下一次 Cron 时间,再向 Redis 发布事件。该文件明确保留了"实际任务队列尚待接入、当前发送给客户端执行"的 TODO。因此 Redis 在这里承担通知和跨进程分发,不是运行 LLM、浏览器或终端工具的执行器。

Webhook 走同一边界。webhook_controller.py先校验触发器、频率和单次执行约束,再落一条 pending 记录;若用户存在活动 WebSocket,会发布事件并等待最多 10 秒确认。没有活动会话时接口仍然成功接收 Webhook,但返回 delivered: falsereason: no_active_sessions。这里所谓"queued"是控制面保存了待执行事实,不等于服务器稍后会自行启动 Agent。

桌面端的订阅 Hook收到 execution_created 后发送 ACK;TriggerTaskExecutor负责创建或恢复 Project 并加入消息队列;BackgroundTaskProcessor每 2 秒扫描一次队列、把执行状态改为 running,再调用普通聊天任务入口。当前实现会避免同一 Project 同时跑多个后台任务,不同 Project 的已启动任务则可以并存。

这也解释了两个运维数字:默认 pending 超过 60 秒未被桌面接管会标记为 missedrunning 超过 600 秒没有完成回报会标记为 failed;连续失败达到 Trigger 配置阈值后还会自动停用。它们是源码默认值,可以通过环境变量或配置改变,不是产品 SLA。要实现真正"无人值守",至少要保证桌面应用、WebSocket、本地 Brain、模型和所需浏览器/Connector 长期在线;若希望只部署服务端就持续执行,则还需要补齐服务端 Agent Worker、任务领取、租约、幂等、重试和资源隔离,而不能只增加 Celery 并发。

三、Agent 与 Workforce 内核:规划、分配、执行、失败和记忆

3.1 Workforce:Eigent 包装 CAMEL,而不是重写一套调度器

复杂任务进入 Workforce 后,construct_workforce() 会并行创建以下对象:

  • 协调 Agent:根据 Worker 描述和任务状态做分配;
  • 任务规划 Agent:把主任务拆为带依赖的子任务;
  • 新 Worker Agent:需要时辅助生成定制 Worker;
  • Developer、Browser、Document、Multi-Modal 四类预置专业 Worker;
  • MCP 搜索/安装相关 Agent;
  • 用户另外配置的自定义 Worker。

这里"并行创建 Agent"使用 asyncio.gather()asyncio.to_thread(),优化的是启动等待时间;真正的子任务发布、Worker 监听、结果回传和依赖处理来自 CAMEL 的 Workforce 与 TaskChannel。Eigent 的 Workforce 子类主要增加了 UI 事件、流式分解、失败兜底、超时、清理和本地上下文接入。

一次复杂任务的执行分为两个明显阶段:

text 复制代码
阶段 A:规划
  question_confirm 判断是否复杂
    → eigent_make_sub_tasks()
    → task_agent 流式生成子任务
    → 更新依赖并通过 SSE 展示
    → 用户可增删改任务

阶段 B:执行
  用户确认 Start
    → eigent_start() 把编辑后的任务放入 pending deque
    → CAMEL Workforce 分配给 Worker Node
    → Worker 调模型并调用工具
    → 结果回到 TaskChannel,依赖任务继续
    → Eigent 同步任务状态、结果、失败与最终汇总

这个"先规划、可人工调整、再执行"的停顿非常重要:规划器输出不是不可更改的真理。对于会写文件、发消息、修改外部数据或调用高成本模型的任务,执行前检查任务拆分、Worker 和工具范围,通常比事后补救更便宜。

当前包装层为单个返回任务设置 3600 秒等待超时,并启用 CAMEL 的 retryreplan 失败策略;_analyze_task() 在结构化输出无效时最多重试三次,仍失败则按场景终止或接受已有结果。这里的数字是代码配置,不是 SLA。模型供应商超时、浏览器卡住、工具副作用和外部服务幂等仍需单独治理。

3.2 Single Agent:跳过 Workforce,但仍然是带工具的执行器

session_mode == "single-agent" 时,step_solve() 直接进入 single_agent_solve(),不会创建协调器、规划器和任务树。Agent 通过 astep() 处理当前目标,工具调用和模型输出仍会转成 SSE 事件。默认工具装配包括人工交互、文件、Web 预览、截图、Skills、Todo、搜索、浏览器、终端、Web Fetch、Planning Worktree、MCP 和有限深度的 Agent 委派,实际可用项还要经过部署能力与用户配置过滤。

单 Agent 默认委派深度为 1:根 Agent 可以创建一层子 Agent,子 Agent 不再继续递归。它避免无限生成 Agent,但不代表每个模型都能稳定完成委派;工具调用能力、提示词遵循和上下文容量仍由所选模型决定。

选择原则可以很简单:

  • 修改一个明确文件、运行一组测试、连续追问同一问题:优先 Single Agent;
  • 调研资料、实现代码、生成文档和检查效果能够拆成不同工作包:考虑 Workforce;
  • 包含外部写操作:无论哪种模式,都先减少工具权限并保留人工确认点。

3.3 Remote Sub Agent:受策略约束的委派工具,不自动继承本地工作区

官方的 Gemini Managed Agents 用例展示了本地编排与远端 Agent 之间的两层协作。源码中的实现方式不是再创建一个本地 CAMEL Worker;在启用且 Provider 配置完整时,各类 Agent 工厂会调用 attach_remote_sub_agent_if_enabled(),给 Developer、Browser、Document、Multi-Modal、Social、MCP、新建 Worker 和自定义 Worker 追加 run_remote_sub_agent FunctionTool。模型仍由原 Workforce/Agent 决定何时委派,远端结果再作为工具返回值进入本地推理链。

当前固定提交注册的 Provider 只有 Gemini Agents API。RemoteSubAgentRuntime先检查启用状态、Provider 白名单和最长运行时间,再流式消费 Provider 事件;Gemini 适配器把请求发送到 /interactions,并可用 previous_interaction_id 与远端 environment_id 延续会话。

会话复用并不等于持久化记忆。session_store.pyproject_id + provider + remote_agent_name 组成默认键,把交互 ID 和环境 ID 保存在带锁的进程内字典中。它可以让同一 Brain 进程内的后续委派继续远端上下文,但 Brain 重启后会丢失,也没有展示多进程共享存储;因此不能把它等同于下一节介绍的项目级本地记忆。

Remote Sub Agent 的数据边界尤其重要:

边界 固定提交中的行为
默认状态 关闭;只有 enabled 且 Provider 的 API Key、Base URL、Agent Name 完整时才暴露工具
Provider 当前注册表只有 gemini_agents,并检查允许列表
运行时间 默认最长 600 秒,可由 Provider 配置调整
本地文件 不自动上传,也不能直接读取本地工作目录;必须把必要文本放进 instruction,或提供远端可访问的 HTTP(S) URL
Skills 远端环境不能读取本地 SKILL.md;需要由调用方筛选后通过 skill_context 明确传入
会话 可复用 interaction/environment,但状态只保存在当前 Brain 进程内
快照 当前配置路径禁止下载,不存在自动回传本地文件的能力

RemoteSubAgentToolkit的公开工具参数只有 instruction、远端 Agent 名称、系统指令、是否复用会话和 skill_context,没有本地文件上传参数。虽然Policy还定义了工作目录约束、50 MB 快照上限,以及 .env.ssh、私钥、token、secret、credential 等拒绝模式,但当前工具调用链没有启用快照下载,也没有调用文件范围检查完成自动同步。更准确的理解是:这些字段为文件/快照能力预留了安全规则,不代表本地工作区已经安全地镜像到远端。

因此,适合交给远端的是边界清楚、可以仅靠提示文本或公开 URL 完成的研究、日志分析和隔离计算;涉及未提交源码、客户附件、密钥、内部 URL 或本地 Skill 时,应先做最小化、脱敏和可访问性设计。远端 Agent 返回的结论也仍是外部结果,涉及本地文件写入或业务副作用时,应回到本地受控工具执行,而不是把"远端运行"误解为自动获得了本机权限。

3.4 项目记忆是本地结构化上下文,不是默认向量 RAG

Eigent 当前的项目记忆采用以下本地目录结构:

text 复制代码
~/.eigent/memory/
  users/<canonical_user_id>/
    spaces/<space_id>/
      projects/<project_id>/
        project.json
        conversation.jsonl
        summary.md
        facts.json
        artifacts.json
        runs/<run_id>/
          run.json
          status.json
          tool_events.jsonl

Run 开始时写入用户问题和运行状态,结束时写入最终回答、摘要和状态;ProjectContextBuilder 从项目摘要、最近对话、事实和可用于上下文的产物中组装提示词。默认预算约 8000 Token,以"约 4 字符/Token"做粗略分配,最近对话最多读取 24 条,并让最近对话占主要预算。写入是 best-effort:记忆文件失败会记录日志,但不会让聊天任务失败。

需要注意三层边界:

  1. 这是本地 JSON/JSONL/Markdown 存储和预算化提示词拼装,不是自动对全部项目文件建立向量索引。
  2. RAGToolkit 确实存在,但它是可给自定义 Worker 选择的工具,封装 CAMEL Retrieval、OpenAI Embedding 与本地 Qdrant;它不是每次 Eigent 对话必经的核心链路。
  3. 当前 workforce_worker 的专属上下文渲染仍较窄,源码注释也把更完整的按角色记忆拆分列为后续工作。因此不能宣称所有 Worker 自动共享同一份完整长期记忆。

对话上下文、项目文件和 RAG 是三件不同的事:前者解决跨 Run 连续性,第二类是 Agent 当前可读取的事实源,第三类才是按查询召回候选。需要知识库效果时,应明确建立索引、定义数据更新和评测,而不是把"选择了文件夹"直接等同于 RAG。

四、模型、工具、MCP 与安全边界:Agent 到底能做什么

4.1 模型层统一了入口,没有抹平模型差异

agent_model() 将前端提供的 model_platformmodel_typeapi_keyapi_url、额外参数和每个自定义 Worker 的专属配置交给 CAMEL ModelFactory.create()。上层 Agent 因而可以接 Eigent Cloud、BYOK、OpenAI 兼容端点或本地推理服务;官方文档列出的本地方案包括 Ollama、vLLM、SGLang、LM Studio 和 LLaMA.cpp。

图片来源:Eigent 官方 Self-hosting 文档

源码还对不同角色和平台做了少量适配:任务规划 Agent 强制流式输出;OpenAI 家族的 Browser Agent 默认关闭并行工具调用;Anthropic/Bedrock 设置缓存控制;OpenAI 使用 Project ID 作为 Prompt Cache Key;订阅运行时会刷新凭据并控制存储/流式参数。

但"模型无关"应理解为统一接入层,而不是无成本替换。换模型时至少要验证:

  • 是否可靠支持 Function/Tool Calling;
  • 上下文长度与结构化输出稳定性;
  • 图片、音频等多模态能力;
  • 流式格式、Token 统计和超时参数;
  • 本地端点是否真正兼容所需 OpenAI API;
  • 速度、费用、并发配额和数据合规。

能完成普通聊天的模型,不一定能稳定驱动多 Agent 任务分解和工具循环。更稳妥的做法是先用 Single Agent 完成一组可复现任务,再启用 Workforce 做相同任务的回归比较。

4.2 工具暴露分为预置 Toolkit、MCP、Skills 和人工交互

Eigent 的工具层不是一个全局"工具箱"直接塞给所有模型:

类型 Eigent 自有逻辑 外部依赖逻辑 暴露范围
预置 Toolkit 为工具增加任务 ID、工作目录、SSE 事件和清理 文件、终端、浏览器等基础实现多来自 CAMEL 按 Agent 工厂和部署能力装配
自定义 Worker 工具 根据用户选择创建 Toolkit FunctionTool 调用循环由 CAMEL Agent 执行 仅当前 Worker 的选择范围
MCP 过滤 Server、补充认证目录、连接与收集工具 MCP 协议和客户端来自 CAMEL Single Agent 为配置中允许的 Server;自定义 Worker 为显式选择的 Server
Skills 读取用户配置、按 Agent 范围过滤 Skill Skill 的发现、读取与调用由 CAMEL SkillToolkit 承担 全局或指定 Agent
Human Toolkit 把问题写入任务队列并等待 GUI 回复 需要澄清、凭据或决定时暂停

浏览器工具还有一条桌面专有装配链。Electron Main 在主进程入口管理 CDP Browser Pool、端口、独立 Profile 和健康检查,Preload 通过受控 IPC 将浏览器池能力交给渲染进程;一次 Chat/Run 再把 CDP Endpoint 冻结进 RunContext,Brain 的 toolkit_assembler.py据此创建 HybridBrowserToolkit。这解决了 Agent 与真实桌面浏览器协作的问题,但 Profile 隔离和端口管理不能被解释为强安全沙箱。

对 Single Agent 而言,installed_mcp 中通过 Hands 过滤的 Server 会被连接,Server 返回的工具集合整体加入该 Agent;当前代码没有在工具装配前按本次问题再做向量 Top-K 路由。对自定义 Worker,MCP 范围来自该 Worker 的 mcp_tools。因此应按任务域拆分 Connector,避免把大量相似或高风险工具同时暴露给一个模型。

Skills 也不能被当作无害文本。官方文档支持上传 SKILL.md 或包含它的 ZIP;Skill 可以带脚本、模板和操作流程。只从可信来源安装,检查其文件、命令、网络目标和密钥读取方式,再限定到确实需要的 Agent。

4.3 Hands/Sandbox 与两套后端的认证边界

Brain 启动时通过 BrainCapabilities 判断部署环境:

环境 文件系统意图 终端 浏览器 MCP
本机/Electron full 检测本机 Shell CDP 可用时开启 默认全部
Docker/Sandbox workspace_only 容器存在 Shell 时仍可能开启 默认关闭 默认全部,可配置 allowlist
RemoteHands 由远端集群能力决定 远端能力 远端能力 远端能力

工具装配阶段会实际依据 Hands 过滤 Terminal、Browser 和 MCP。can_access_filesystem() 的调用点主要用于 workspace 绑定路径校验的回退,并未贯穿所有文件与终端工具路径;文件 API 自己使用 resolve_under_base() 防止路径逃逸,文件 Toolkit 依靠工作目录与 CAMEL 基类,终端则以 safe_mode=True 调用 CAMEL TerminalToolkit,没有在 Eigent 代码里传入明确 allowed_commands

所以最准确的结论是:Eigent 已有部署感知的能力清单、工作区路径校验和工具级门控,但类名 SandboxHandsworkspace_onlysafe_mode 本身不能证明强隔离。若任务会运行不可信命令或处理敏感数据,仍需使用容器/虚拟机、非特权用户、只读挂载、网络出口策略、CPU/内存/时间限制和一次性凭据。模型生成的命令始终应视为不可信输入。

server/ 控制面实现了本地用户、JWT、Token 黑名单、资源所有权检查,并对远程控制等敏感接口设置 Redis 限流。Brain 的非健康路由虽然统一挂上了认证依赖接口,但默认实现是 NoneAuth,会信任请求并给出固定 local/default 身份;run_standalone() 默认还绑定 0.0.0.0

桌面 Electron 启动 Brain 时默认只在本机端口工作,这个信任模型尚可理解;独立部署时则不能把 5001 直接暴露到公网。应至少绑定 127.0.0.1、通过受认证的反向代理访问,或实现并启用真正的 Brain Auth Provider。不要把 server/ 已登录误认为 Brain 的每个执行 API 已自动拥有同等身份校验。

五、安装与部署:从快速体验到完全本地

5.1 从源码启动桌面端:默认连接 Eigent 云服务

官方根 README 给出的开发启动方式需要 Node.js 18~22:

bash 复制代码
git clone https://github.com/eigent-ai/eigent.git
cd eigent
npm install
npm run dev

这条路径会启动 Electron/React,并准备 Brain 依赖,但默认连接 Eigent 云服务且需要账户。第一次启动可能下载 Python、前端和浏览器相关依赖,耗时明显长于普通 Vite 项目。拉取新代码后,如果两个依赖锁都变化,应同时更新:

bash 复制代码
npm install
cd backend
uv sync

Brain 的 backend/pyproject.toml 当前要求 Python >=3.11,<3.12;Electron 会管理对应环境。不要因为 server/ 使用 Python 3.12 就让两套 Python 环境混用。

5.2 完全本地:先启动控制面,再让桌面指向它

官方 server/README_EN.md 的本地部署由 PostgreSQL、Redis、API、Celery Worker 和 Celery Beat 组成。server/ 当前要求 Python >=3.12,<3.13,但 Docker 镜像已经包含该环境。先复制环境配置并启动:

bash 复制代码
cd server
cp .env.example .env
docker compose up --build -d

然后在仓库根目录的 .env.development 确认:

dotenv 复制代码
VITE_BASE_URL=/api
VITE_USE_LOCAL_PROXY=true
VITE_PROXY_URL=http://localhost:3001

再启动桌面开发应用:

bash 复制代码
cd ..
npm install
npm run dev

当前 Compose 端口关系为:API 3001 → 5678、PostgreSQL 5432 → 5432、Redis 6379 → 6379;数据库保存在 Compose 的 postgres_data 卷。基础验证命令:

bash 复制代码
docker compose -f server/docker-compose.yml ps
curl http://localhost:3001/health

浏览器打开 http://localhost:3001/docs 可查看本地控制面 Swagger。进入 Eigent 后,还要在 Agents → Models 配置一个可用 Provider;"服务都健康"并不代表已有可执行模型。完全离线还需只使用本地模型和本地 MCP,关闭云 Provider、远程 Connector 及其他外部请求。

5.3 跑通第一个可验证任务

服务健康只说明入口可访问,不能证明 Agent 已经拥有模型、目录和工具。第一次使用建议建立一个小而可复核的闭环:

  1. 在 Agents → Models 配置一个可用 Provider,并先完成普通对话测试;
  2. 新建测试 Space,选择一个专用本地目录,避免直接对重要仓库使用 direct-write
  3. 使用 Single Agent 执行"读取两个文本文件并在 output/summary.md 生成摘要"一类结果明确的任务;
  4. 对照任务树、终端/工具事件和文件预览,确认产物真实写入本次 Run 的目录;
  5. 再用 Workforce 执行同类可拆分任务,检查规划、Worker 分配与最终文件是否比 Single Agent 更合理;
  6. 接入 MCP 或外部 Connector 时先执行只读操作,核对它只出现在被授权的 Agent 范围。

成功判据不是界面出现一段回答,而是目标文件真实落盘、内容能够人工复核、工具事件与目录一致,停止或重新打开任务后仍能定位本次 Run。若其中任一项失败,应先检查模型工具调用兼容性、工作目录模式和 Brain 事件,再讨论多 Agent 效果。

5.4 生产前必须改掉示例配置

仓库 Compose 更接近可复现的本地环境,不是开箱即用的公网生产基线。至少完成以下处理:

  • 将 PostgreSQL 示例密码 123456secret_key=postgres、聊天分享密钥和 Salt 全部替换为高强度随机值;
  • 不向公网发布 5432 和 6379,Redis 默认 Compose 没有配置认证;
  • API 前置 HTTPS 反向代理,严格配置 CORS、Webhook 域名和可信代理;
  • Brain 只监听本地/私网,并补充真实认证;
  • 模型、MCP、Slack 等密钥使用专用 Secret 管理,不写入 Git、日志或截图;
  • 备份 PostgreSQL 卷、用户配置、工作目录与 ~/.eigent/memory,并实际演练恢复;
  • 固定发布标签或提交,不让生产环境无测试地跟随 main
  • 对外部写操作建立人工确认、幂等键、超时、重试上限和审计记录。

源码根 LICENSE 与 README 声明 Apache License 2.0,但 package.jsonlicense 字段仍写为 MIT。分发修改版或商业集成前应以完整许可证文件为基础,并向上游确认元数据差异,不要只读取包字段做合规判断。

六、工程边界、适用场景与落地建议

6.1 运行状态、认证、数据出网与并发边界

Brain 当前把运行中的 TaskLock、动作队列和 Agent 内存保存在进程内;Trigger 虽由 server/ 的 Celery Beat 调度,真正执行仍依赖在线桌面接收事件。这意味着"可以同时看到多个任务"不等于已经具备无状态横向扩容。容量还会受模型配额、浏览器 Profile、本机终端、目录 I/O 和 Connector 上游限额共同影响。

当前公开源码没有给出可复现的吞吐、P95 时延或稳定并发报告。生产评估应使用自己的任务组合记录 Run 创建、首个事件、工具耗时、人工等待、产物成功率和失败恢复;若要部署多个 Brain,还需补会话粘性、状态外置以及浏览器和终端资源归属。

server/ 的 JWT 和资源检查不能自动覆盖默认使用 NoneAuth 的 Brain。Hands 提供部署感知的能力门控,但不是容器或虚拟机隔离证明;云模型、远程 MCP 和 Connector 还可能把项目内容发送到外部服务。公网部署必须收紧 Brain 监听与认证,把密钥放入专用 Secret 管理,并对文件写入、终端、浏览器和外部写操作应用最小权限与人工确认。

6.2 适用场景与落地顺序

Eigent 适合以下场景:围绕本地代码库持续开发与测试;同时需要网页调研、数据整理、报告/PPT/表格产出的复合任务;希望用 MCP 接入日历、文档、协作平台或内部服务;希望保留项目文件、Run 和产物,而不是每次从空白聊天开始。

它不天然解决所有企业平台问题。本地模型质量和工具调用兼容性差异很大,跨地域高可用、复杂 RBAC、集中审计、数据防泄漏和大规模任务队列仍需要额外架构。

建议按下面顺序落地:

  1. 先选一个输入、产物和验收标准都清晰的项目;
  2. 用 Single Agent 验证工作目录、模型、文件/终端和最终产物;
  3. 建立任务集,记录成功率、人工介入、Token、耗时和副作用;
  4. 只有任务确实可拆分时再使用 Workforce,并检查规划结果后启动;
  5. MCP 与 Skills 从最小集合开始,外部写操作单独授权;
  6. 最后补齐认证、容器隔离、网络策略、密钥、备份、监控和回滚。

从源码看,Eigent 的价值并不是发明了新的多智能体算法,而是把 CAMEL Workforce、模型与工具能力组织成一个能选择项目目录、看见执行过程、管理 Run 和接收真实产物的桌面工作环境。它把 Agent 从"回答问题"推进到"在上下文和工具边界内完成任务";真正决定生产可用性的,则是任务设计、模型评测、最小权限和可靠运维。

参考资料

  1. Eigent GitHub 仓库:https://github.com/cmyk-labs/eigent
  2. Eigent 官方 GitHub 仓库:https://github.com/eigent-ai/eigent
  3. Eigent 官方文档:https://www.eigent.ai/docs/
相关推荐
汐ya~2 天前
【MaxKB 技术全景】开源企业级知识库 RAG、工作流智能体、工具生态与生产部署
github开源·企业级rag知识库·工作流agent·mcp/skills/工具
汐ya~3 天前
【PageEyes Agent 跨端 UI 自动化】开源Pydantic AI、OmniParser 多源感知的UI 自动化Agent
计算机视觉·agent·ui自动化·github开源