DeerFlow 只有一个账号,如何服务多个业务用户?——业务系统、智能体与 MCP 调用全流程
最近在研究 DeerFlow 与业务系统集成时,我遇到一个很实际的问题:如果 DeerFlow 只有一个管理员账号,而业务系统里有很多员工,怎样让所有员工使用同一个智能体,同时又只能查看和操作自己的数据?
本文通过一个“任务助理”的例子,把业务系统 → DeerFlow 智能体 → MCP → 业务系统这条链路讲清楚。尽量不用复杂术语,重点解释每一层负责什么,以及用户身份、会话和数据权限如何保持正确。
本文以一套智能办公工作台的集成设计为例。接口路径、工具名和 ID 均为该示例中的约定或示意,不代表每一套 DeerFlow 部署都使用相同配置。
一、先理解三个角色
假设公司已经有一套智能办公工作台,员工在里面管理自己的待办任务。我们还部署了 DeerFlow,并创建了一个“任务助理”智能体,配置好任务相关的 MCP 工具。
| 组成 | 通俗理解 | 主要职责 |
|---|---|---|
| 智能办公工作台 | 业务系统、真正的“管家” | 识别登录员工、管理会话、检查权限、保存和修改真实任务 |
| DeerFlow 智能体 | 会听懂人话的“助理” | 理解问题、结合上下文、决定调用什么工具、组织回复 |
| MCP 服务 | 智能体与业务系统之间的“工具接口” | 把查询任务、准备任务草稿等工具请求转给业务后端 |
最重要的一点:DeerFlow 负责理解和执行对话流程,不能因为它能调用 MCP,就默认它有权查看或修改全部业务数据。 最终权限仍由工作台后端判断。
二、整体调用关系是什么样的?
张三(登录智能办公工作台)
│
│ 发送问题 + 工作台会话 WB-01
▼
智能办公工作台后端(Go)
├─ 验证登录身份:user-zhang
├─ 检查会话归属
├─ 关联 DeerFlow 线程:DF-01
└─ 为本次执行提供受限 MCP 凭据
│
▼
DeerFlow 任务助理(DF-01)
└─ 理解问题,选择 list_tasks 等工具
│
▼
MCP 服务:office-task-local
└─ 验证短时凭据,转交业务请求
│
▼
工作台业务接口及数据库
└─ 按张三的真实权限查询或处理任务
│
▼
结果原路返回:MCP → DeerFlow → 工作台 → 张三
这看起来绕了一圈,但每一层的作用都很明确:工作台认人和管数据,DeerFlow 理解需求,MCP 提供工具通道。
三、第一轮对话:张三查询今天的待办任务
张三已经登录智能办公工作台,并新建了一个任务助理会话。他问:
我今天有哪些待办任务?
第 1 步:工作台先收到消息
浏览器向工作台后端发送请求:
POST /api/v1/assistant/task/ag-ui
Cookie: office_session=<浏览器登录会话>
请求还会带上当前工作台会话 WB-01 和用户输入的文字。这里的 AG-UI 是工作台对话接口使用的交互形式;工作台后端负责再对接 DeerFlow,不能把它简单理解为“浏览器直接访问 DeerFlow”。
第 2 步:工作台确认“谁在提问”
后端通过登录 Cookie 检查当前用户,确认是张三,得到可信的业务用户 ID,例如:
user-zhang
注意:不是让大模型从一句“我是张三”里判断身份。 用户身份必须来自业务系统已经验证过的登录信息。
第 3 步:找到对应的 DeerFlow 会话
工作台保存一条映射关系:
业务用户:user-zhang
工作台会话:WB-01
DeerFlow 线程:DF-01
第一次聊天时创建或关联 DF-01,后续张三在同一个工作台会话里继续提问,就复用该线程。
第 4 步:工作台调用 DeerFlow
示例项目使用的 DeerFlow 流式运行接口形式是:
POST /api/threads/DF-01/runs/stream
工作台把问题和必要的服务端上下文交给 DeerFlow,并为本次运行提供受限的 MCP 访问凭据。用户 ID 可以出现在上下文中,方便智能体理解,但不能仅凭这段文字授权访问数据。
第 5 步:DeerFlow 调用 MCP 查询任务
智能体发现这个问题需要查询任务,于是调用提前注册好的工具:
MCP 服务:office-task-local
工具:list_tasks
参数:{"range":"today","status":"pending"}
这些工具名和参数结构由 MCP 预先定义。大模型负责选择和填写参数,不能随意创造后端不存在的接口。
第 6 步:MCP 和业务后端校验权限
MCP 请求携带工作台后端签发的短时、受限凭据。服务端校验其签名、有效期、所属用户、会话及可执行操作范围,再按张三的业务权限查询数据。
因此,即使 DeerFlow 只有一个管理员账号,也不能直接把这个管理员身份当作所有员工的业务身份。
第 7 步:结果返回给张三
工作台后端返回张三有权访问的待办数据,MCP 将结果交给 DeerFlow,智能体整理成自然语言,再通过工作台的原始对话请求流式显示出来。
到这里,完成的是一次“读取数据”操作。
四、第二轮对话:张三让智能体创建任务
张三接着在同一个会话中说:
帮我新建一个办公室路由器接线任务。
这时与查询不同,因为涉及写入业务数据,不能让智能体一句话就直接落库。
第 1 步:继续使用原会话
工作台再次验证张三的登录状态,确认仍是 user-zhang 的 WB-01,继续使用 DeerFlow 线程 DF-01。这样智能体可以接着前面的对话理解需求。
第 2 步:智能体补全任务信息
智能体可能需要进一步确认负责人、截止日期或所属项目。信息足够后,调用 MCP 的“准备草稿”工具:
MCP 服务:office-task-local
工具:propose_task_action
示例参数:
{
"action": "create",
"title": "办公室路由器接线",
"description": "完成办公室路由器接线"
}
第 3 步:MCP 返回待确认草稿
MCP 服务验证短时凭据以及张三的相关权限,生成一条待确认的任务草稿,并返回 proposal_id。
此时需要特别注意:只是生成草稿,还没有正式创建任务。
第 4 步:张三在工作台确认
工作台向张三展示草稿,可以修改、确认或取消。
只有张三点击“确认创建”后,工作台 Go 后端才会重新检查:登录身份、草稿所属用户和会话、版本、有效期、业务权限等,最后通过数据库事务正式创建任务并保存操作回执。
这里的设计很重要:最终写入不是再让 DeerFlow 调 MCP 去“确认创建”,而是由工作台后端完成。 这样可以防止模型误操作、重复创建,也方便审计。
五、只有一个 DeerFlow 账号,怎么区分不同员工?
答案是:DeerFlow 登录账号与业务系统员工身份不是同一个概念。
可以由工作台后端统一接入 DeerFlow,不要求每个员工都注册 DeerFlow 登录账号。但每位员工的业务身份、会话映射和数据权限仍然必须单独管理。
例如:
| 业务用户 | 工作台会话 | DeerFlow 线程 | 含义 |
|---|---|---|---|
| 张三(user-zhang) | WB-01 | DF-01 | 张三的第一段任务对话 |
| 张三(user-zhang) | WB-02 | DF-02 | 张三新开的另一段对话 |
| 其他员工 | WB-03 | DF-03 | 另一个员工的独立会话 |
工作台每次收到消息,都要重新校验当前登录用户是否有权访问该工作台会话及对应线程,不能让客户端随意传一个 DF-01 就读取里面的内容。
还要补充一个容易被忽略的细节:不同线程有独立对话上下文,不等于 DeerFlow 单账号下所有长期记忆、文件和工作区都会自动按业务用户隔离。 如果启用这些能力,还要分别验证存储路径、读取权限和用户作用域,必要时增加业务层隔离。
六、为什么不直接把 user_id 交给智能体,让它调用 MCP?
假设模型调用工具时传入:
{"user_id":"user-zhang","range":"today"}
仅凭这个参数是不安全的。因为用户可能在聊天中说“帮我查询别人的任务”,模型也可能生成不正确的 ID。
正确思路是:
- 工作台后端确认真实身份,例如
user-zhang。 - 为本次运行签发短时、最小权限的访问凭据,绑定用户、会话、运行 ID、允许操作及过期时间。
- MCP 服务端验证凭据,并由业务后端再次执行数据权限判断。
- 模型提供的参数只描述想做什么,不能决定它有权查看谁的数据。
凭据应通过受控的服务端调用机制传递,不应直接写入用户可编辑的 Prompt,也不应作为普通聊天内容展示或记录。
一句话:身份由后端证明,权限由后端执行,智能体只负责提出工具调用请求。
七、任务创建成功后,智能体如何知道最终执行结果?
假设张三让智能体创建“办公室路由器接线”任务。智能体通过 MCP 生成了待确认草稿,张三在业务系统中点击“确认创建”,随后又问:
刚才那个路由器接线任务创建成功了吗?
这里有一个容易忽略的问题:生成任务草稿和正式创建任务是两个不同的操作。 DeerFlow 知道自己生成过草稿,但如果没有取得业务系统的最终执行结果,就无法确认任务是否真正创建成功。
1. 正规实现:以业务系统的操作回执为准
建议把任务处理设计成一个可追踪的闭环:
- 生成草稿: DeerFlow 调用 MCP 准备任务草稿,业务系统返回唯一的
proposal_id。 - 用户确认: 张三在业务页面检查任务信息,点击“确认创建”。
- 正式执行: 业务系统后端再次验证张三的身份、任务权限和草稿状态,完成数据库写入。
- 保存回执: 业务系统记录本次操作的
operation_id、proposal_id、执行状态、任务 ID 和执行时间等信息。状态可以是成功、失败或取消。 - 获取结果: 工作台将可信的操作结果提供给后续 DeerFlow 对话,或让智能体通过只读 MCP 查询工具获取最新状态。
- 回复用户: DeerFlow 根据实际结果回答“创建成功”“创建失败”或“仍在处理中”,不自行猜测。
整体流程可以概括为:
张三确认创建任务
↓
业务系统校验权限并执行写入
↓
保存任务和操作回执(operation_id)
↓
工作台补充可信执行结果 / MCP 查询操作状态
↓
DeerFlow 获取实际结果并回复张三
2. 如何把执行结果提供给 DeerFlow?
通常有两种方式,可以根据业务需要组合使用:
| 方式 | 实现思路 | 适用场景 |
|---|---|---|
| 下一轮补充上下文 | 工作台在下一次调用 DeerFlow 前,读取当前用户、当前会话的最新操作回执,经过权限检查后作为服务端上下文一并传入 | 让智能体自然接上刚才的操作,减少重复查询 |
| MCP 主动查询 | 提供 get_task_operation_result 等只读工具,智能体需要核实时调用,业务后端返回最新状态 |
操作可能耗时、状态会变化,或者用户主动追问结果 |
例如,张三询问“刚才创建成功了吗”,智能体可以调用只读工具查询与当前会话关联的 operation_id,业务系统返回:
{
"operation_id": "OP-001",
"status": "success",
"task_id": "TASK-001",
"message": "办公室路由器接线任务已创建"
}
DeerFlow 再回复:“创建成功,任务名称为‘办公室路由器接线’。”
这里的 ID 和工具名仅为说明示例,实际使用时以业务系统定义的接口和数据结构为准。
3. 需要特别注意的三点
- 业务系统才是最终事实来源。 DeerFlow 的聊天记录不能替代数据库中的任务状态和操作回执。
- 查询结果也要检查权限。 无论采用上下文补充还是 MCP 查询,都必须确认操作属于当前已验证的用户和会话,不能只相信聊天中传入的
operation_id。 - 核对状态不能重复执行创建。 查询工具应保持只读;正式写入接口应具备幂等控制,避免网络重试或重复点击产生多条相同任务。
简单总结:DeerFlow 负责理解用户意图和解释结果,业务系统负责真正执行并保存操作状态,MCP 或服务端上下文负责把可信结果交给智能体。这样才能形成完整、可靠的业务操作闭环。
八、把整个流程记成四句话
| 场景 | 真正负责的一方 |
|---|---|
| 谁在提问、能看哪些任务? | 工作台后端识别身份并检查权限 |
| 用户想查什么、想创建什么? | DeerFlow 智能体理解语言并选择工具 |
| 怎样把“查询/准备草稿”交给后端? | MCP 服务提供受限工具调用通道 |
| 谁真正把确认后的任务写进数据库? | 工作台 Go 后端完成事务和回执 |
九、总结
DeerFlow 即使只有一个对接账号,也可以作为业务系统统一调用的智能体运行服务。但这不代表所有业务用户都变成同一个人。
在这套设计里,业务用户身份来自工作台登录态;工作台会话与 DeerFlow 线程建立一对一的关联;智能体通过 MCP 查询数据或准备草稿;MCP 和业务后端根据短时凭据及业务权限控制访问;最终创建任务由工作台在用户确认后执行。
最核心的原则是:工作台负责身份、会话映射和真实业务数据;DeerFlow 负责理解对话和选择工具;MCP 负责连接工具与业务后端。不要把“模型知道用户是谁”误当成“用户已经通过权限验证”。
浙公网安备 33010602011771号