mirror of
https://github.com/langbot-app/LangBot.git
synced 2026-09-16 14:57:15 +00:00
feat(runner): unify plugin execution across agents and event processors
This commit is contained in:
@@ -1,6 +1,6 @@
|
||||
# Event Based Agents 架构设计总览
|
||||
|
||||
> Product revision (2026-09-07): [Event processors and Pipeline plugin compatibility](./09-event-processors.md) defines an explicitly bound EventProcessor alongside Pipeline and Agent. It supersedes the automatic EBA observer product model below; the new component and UI are planned, not yet implemented.
|
||||
> Product revision (2026-09-07): [Event processors and Pipeline plugin compatibility](./09-event-processors.md) defines an explicitly bound Runner alongside Pipeline and Agent. It supersedes the automatic EBA observer product model below; the new component and UI are planned, not yet implemented.
|
||||
|
||||
> 当前状态(2026-09-05):平台事件、Bot `event_bindings`、独立 Agent、Pipeline / Agent 平级路由及 WebUI 已集成到 `dev/4.11.x`。实现入口为 `pkg/platform/botmgr.py::RuntimeBot` 与 `pkg/agent/runner/`。下文“当前架构的局限性”“现有架构”描述改造前背景;EventBus / EventRouter 图表示职责划分,不表示存在同名独立服务。当前实现和验收以 [STATUS.md](../agent-runner-pluginization/STATUS.md) 为准,平台动作使用[授权工具](../agent-runner-pluginization/PLATFORM_ACTION_TOOLS.md)。
|
||||
|
||||
@@ -52,9 +52,9 @@ MessageAggregator (消息聚合)
|
||||
QueryPool → Controller → Pipeline (固定阶段链)
|
||||
│ │
|
||||
│ ▼
|
||||
│ AgentRunner Host orchestrator
|
||||
│ Runner Host orchestrator
|
||||
│ ▼
|
||||
│ plugin AgentRunner
|
||||
│ plugin Runner
|
||||
│
|
||||
▼
|
||||
adapter.reply_message() / adapter.send_message()
|
||||
@@ -83,7 +83,7 @@ EventBus (统一事件总线)
|
||||
EventRouter (读取 Bot 的 event_bindings)
|
||||
│
|
||||
├─→ Pipeline target — 完整 Stage 链,仅消息事件
|
||||
├─→ Agent target — 独立 Agent,经插件 AgentRunner 执行
|
||||
├─→ Agent target — 独立 Agent,经插件 Runner 执行
|
||||
└─→ discard — 明确丢弃
|
||||
│
|
||||
▼
|
||||
@@ -150,9 +150,9 @@ pkg/platform/adapters/
|
||||
|
||||
### 3.4 事件响应目标与观察者
|
||||
|
||||
Pipeline 与 Agent 是长期并存、场景不同的同级处理器。Pipeline 保留完整 Stage 链,面向消息处理;Agent 是独立配置对象,选择一个已安装的插件 AgentRunner,并可声明消息或非消息事件能力。Bot 的 `event_bindings` 只负责把事件绑定到既有 Pipeline、独立 Agent 或 `discard`。
|
||||
Pipeline 与 Agent 是长期并存、场景不同的同级处理器。Pipeline 保留完整 Stage 链,面向消息处理;Agent 是独立配置对象,选择一个已安装的插件 Runner,并可声明消息或非消息事件能力。Bot 的 `event_bindings` 只负责把事件绑定到既有 Pipeline、独立 Agent 或 `discard`。
|
||||
|
||||
插件 EventListener 是观察者:事件先广播给有权限的监听器,随后路由器再选择一个响应目标。Webhook、Dify、n8n 等外部执行方式若需要作为响应者,应由对应 AgentRunner 插件表达,而不是增加另一套 Host Handler 主链。
|
||||
插件 EventListener 是观察者:事件先广播给有权限的监听器,随后路由器再选择一个响应目标。Webhook、Dify、n8n 等外部执行方式若需要作为响应者,应由对应 Runner 插件表达,而不是增加另一套 Host Handler 主链。
|
||||
|
||||
现有 Pipeline 不会被转换为 Agent,Pipeline 内的 runner 配置也不会复制到独立 Agent。用户需要 Agent 时自行创建并绑定。
|
||||
|
||||
@@ -174,7 +174,7 @@ Pipeline 与 Agent 是长期并存、场景不同的同级处理器。Pipeline
|
||||
| 2 | 适配器特有 API | 统一抽象 + `call_platform_api` 透传 | 通用 API 覆盖大部分场景,透传机制保证灵活性,避免每个适配器导出独立的类型化 API 包 |
|
||||
| 3 | 向后兼容策略 | 兼容层适配 | 保留旧事件类型和 API 作为新系统的 alias/wrapper,现有插件无需修改 |
|
||||
| 4 | 处理器配置存储 | Bot 表使用 `event_bindings`,目标引用原始 Pipeline 或独立 Agent UUID | 路由关系不复制处理器配置,Pipeline/Agent 各自保持事实源 |
|
||||
| 5 | Agent 处理器定位 | 独立 Agent + 插件 AgentRunner | Host 不再内置具体 runner;不同 AgentRunner 通过统一协议接入 |
|
||||
| 5 | Agent 处理器定位 | 独立 Agent + 插件 Runner | Host 不再内置具体 runner;不同 Runner 通过统一协议接入 |
|
||||
| 6 | 事件命名方式 | 命名空间式(`message.received`) | 清晰的分类层级,便于通配匹配(`message.*`),与 WebUI 配置天然对应 |
|
||||
|
||||
## 5. 文档索引
|
||||
@@ -194,7 +194,7 @@ Pipeline 与 Agent 是长期并存、场景不同的同级处理器。Pipeline
|
||||
| 仓库 | 改动范围 |
|
||||
|------|----------|
|
||||
| **langbot-plugin-sdk** | 事件定义、实体模型、API 接口、适配器基类、通信协议扩展 |
|
||||
| **LangBot**(后端) | 适配器实现、事件路由引擎、Bot/Agent 实体、AgentRunner Host 编排 |
|
||||
| **LangBot**(后端) | 适配器实现、事件路由引擎、Bot/Agent 实体、Runner Host 编排 |
|
||||
| **LangBot**(前端) | Bot 事件处理器编排面板 |
|
||||
| **langbot-wiki** | 新架构文档、插件开发指南更新、适配器开发指南 |
|
||||
| **langbot-plugin-demo** | 示例更新(使用新事件和 API) |
|
||||
|
||||
@@ -499,7 +499,7 @@ class PlatformSpecificEvent(Event):
|
||||
│
|
||||
8. 目标处理事件
|
||||
│ Pipeline → 进入完整 Pipeline 流水线(仅消息事件)
|
||||
│ Agent → Host 编排已安装的插件 AgentRunner
|
||||
│ Agent → Host 编排已安装的插件 Runner
|
||||
│ discard → 不产生响应
|
||||
│
|
||||
9. 处理器执行完毕,可能通过 Host 授权 API 执行响应动作
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
# 事件路由与编排
|
||||
|
||||
> Implementation update (2026-09-08): the EventListener observer-broadcast proposal below is superseded by [Event processors](09-event-processors.md). Legacy EventListener hooks run only inside Pipeline. New EBA handlers use explicitly created and bound EventProcessor instances, a third peer processor type alongside Agent and Pipeline.
|
||||
> Implementation update (2026-09-08): the EventListener observer-broadcast proposal below is superseded by [Event processors](09-event-processors.md). Legacy EventListener hooks run only inside Pipeline. New EBA handlers use explicitly created and bound Runner instances, a third peer processor type alongside Agent and Pipeline.
|
||||
|
||||
> 状态:当前实施模型(2026-07-12)。本文以 Pipeline / Agent 平级并存为准,不再保留早期 `pipeline / agent / webhook / plugin` 四种 Handler 草案。
|
||||
|
||||
@@ -16,10 +16,10 @@ Pipeline 与 Agent 是平级处理器:
|
||||
| 处理器 | 配置事实源 | 执行路径 | 事件范围 |
|
||||
| --- | --- | --- | --- |
|
||||
| Pipeline | Pipeline 表与完整 Stage 配置 | MessageAggregator -> QueryPool -> RuntimePipeline | 消息事件,首版为 `message.received` |
|
||||
| Agent | Agent 表中的 runner 与 runner config | AgentRunner Host orchestrator -> plugin AgentRunner | Agent/Runner 声明支持的消息或非消息事件 |
|
||||
| Agent | Agent 表中的 runner 与 runner config | Runner Host orchestrator -> plugin Runner | Agent/Runner 声明支持的消息或非消息事件 |
|
||||
| discard | 无处理器配置 | 明确结束路由 | 任意事件 |
|
||||
|
||||
插件 EventListener 不是第三种响应目标。Webhook、Dify、n8n、Coze 等外部系统需要响应事件时,由对应 AgentRunner 插件承接。
|
||||
插件 EventListener 不是第三种响应目标。Webhook、Dify、n8n、Coze 等外部系统需要响应事件时,由对应 Runner 插件承接。
|
||||
|
||||
## 2. 数据模型
|
||||
|
||||
@@ -34,7 +34,7 @@ class Agent(Base):
|
||||
description: str
|
||||
emoji: str
|
||||
kind: str # 固定为 "agent"
|
||||
component_ref: str # AgentRunner id
|
||||
component_ref: str # Runner id
|
||||
config: dict # runner + runner_config
|
||||
supported_event_patterns: list[str]
|
||||
```
|
||||
@@ -57,7 +57,7 @@ class Agent(Base):
|
||||
}
|
||||
```
|
||||
|
||||
Runner id 来自已安装插件的 AgentRunner manifest。Host 不维护 LocalAgent、Dify 或其他具体实现的内置分支。
|
||||
Runner id 来自已安装插件的 Runner manifest。Host 不维护 LocalAgent、Dify 或其他具体实现的内置分支。
|
||||
|
||||
### 2.2 EventBinding
|
||||
|
||||
@@ -129,20 +129,20 @@ Platform adapter
|
||||
-> authorized Plugin EventListener observers
|
||||
-> EventRouter
|
||||
-> Pipeline target -> full Pipeline stage chain
|
||||
-> Agent target -> AgentRunner Host orchestrator
|
||||
-> Agent target -> Runner Host orchestrator
|
||||
-> discard -> stop
|
||||
-> Host delivery/platform API
|
||||
```
|
||||
|
||||
### 4.1 Pipeline target
|
||||
|
||||
消息事件按原有方式构造 Query,经 MessageAggregator、QueryPool 和完整 Pipeline Stage 链执行。Pipeline 可以继续使用 AgentRunner 作为 AI stage 的实现,但 Pipeline 本身不会因此变成 Agent。
|
||||
消息事件按原有方式构造 Query,经 MessageAggregator、QueryPool 和完整 Pipeline Stage 链执行。Pipeline 可以继续使用 Runner 作为 AI stage 的实现,但 Pipeline 本身不会因此变成 Agent。
|
||||
|
||||
### 4.2 Agent target
|
||||
|
||||
Host 读取独立 Agent 的 Runner id/config,构造 event-first context、run-scoped resources 与 delivery policy,再调用插件 AgentRunner。Runner 输出由 Host 统一归一化、记录和投递。
|
||||
Host 读取独立 Agent 的 Runner id/config,构造 event-first context、run-scoped resources 与 delivery policy,再调用插件 Runner。Runner 输出由 Host 统一归一化、记录和投递。
|
||||
|
||||
AgentRunner 可通过 SDK/Python `AgentRunAPIProxy.call_tool` 或 SDK-owned scoped MCP bridge 回调 Host 能力。两条路径都映射到 `PluginToRuntimeAction.CALL_TOOL`,使用相同的 run authorization、Host execution Query、ToolManager 和 Box session 规则。Box session 是 Host canonical scope 的固定长度安全哈希;同一平台会话稳定、不同 scope 隔离、缺少 identity 时 fail closed,Runner 不配置 sandbox scope。
|
||||
Runner 可通过 SDK/Python `RunnerAPIProxy.call_tool` 或 SDK-owned scoped MCP bridge 回调 Host 能力。两条路径都映射到 `PluginToRuntimeAction.CALL_TOOL`,使用相同的 run authorization、Host execution Query、ToolManager 和 Box session 规则。Box session 是 Host canonical scope 的固定长度安全哈希;同一平台会话稳定、不同 scope 隔离、缺少 identity 时 fail closed,Runner 不配置 sandbox scope。
|
||||
|
||||
### 4.3 Observer side effects
|
||||
|
||||
@@ -153,7 +153,7 @@ AgentRunner 可通过 SDK/Python `AgentRunAPIProxy.call_tool` 或 SDK-owned scop
|
||||
1. Pipeline 与 Agent 保留各自的持久化、编辑和执行语义。
|
||||
2. 处理器聚合页面可以统一展示二者,但不会创建第三份处理器记录。
|
||||
3. 旧 Pipeline 仍是 Pipeline;其 runner config 不迁移、不复制为独立 Agent。
|
||||
4. 需要 Agent 的用户新建 Agent、选择已安装 AgentRunner,再建立 event binding。
|
||||
4. 需要 Agent 的用户新建 Agent、选择已安装 Runner,再建立 event binding。
|
||||
5. 一个 Bot 可按不同事件同时绑定 Pipeline 与 Agent。
|
||||
|
||||
## 6. WebUI 约束
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
# 插件 SDK 改造
|
||||
|
||||
> Implementation update (2026-09-08): the EventListener observer-broadcast proposal below is superseded by [Event processors](09-event-processors.md). Legacy EventListener hooks run only inside Pipeline. New EBA handlers use explicitly created and bound EventProcessor instances, a third peer processor type alongside Agent and Pipeline.
|
||||
> Implementation update (2026-09-08): the EventListener observer-broadcast proposal below is superseded by [Event processors](09-event-processors.md). Legacy EventListener hooks run only inside Pipeline. New EBA handlers use explicitly created and bound Runner instances, a third peer processor type alongside Agent and Pipeline.
|
||||
|
||||
## 1. 概述
|
||||
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
# EBA 分阶段实施计划
|
||||
|
||||
> Implementation update (2026-09-08): the EventListener observer-broadcast proposal below is superseded by [Event processors](09-event-processors.md). Legacy EventListener hooks run only inside Pipeline. New EBA handlers use explicitly created and bound EventProcessor instances, a third peer processor type alongside Agent and Pipeline.
|
||||
> Implementation update (2026-09-08): the EventListener observer-broadcast proposal below is superseded by [Event processors](09-event-processors.md). Legacy EventListener hooks run only inside Pipeline. New EBA handlers use explicitly created and bound Runner instances, a third peer processor type alongside Agent and Pipeline.
|
||||
|
||||
> 更新:2026-09-05。P0–P4 的主要实现已落入 `dev/4.11.x`,P5 仍需按当前版本验收;下文工作项用于维护实现边界,不表示全部待开发。文件名沿用早期设计,但这里的“迁移”仅指代码架构逐步接入 EBA,不代表 LangBot 3.x 数据库或配置升级。当前提交、定向测试及发布缺口见 [STATUS.md](../agent-runner-pluginization/STATUS.md)。
|
||||
|
||||
@@ -11,15 +11,15 @@ EBA 跨越 SDK、平台适配器、LangBot Host、WebUI 与插件生态,按可
|
||||
- LangBot 4.x 不支持从 3.x 数据库或配置升级;不保留 legacy migration chain、旧 JSON 模板或旧 Runner 字段读取。
|
||||
- Pipeline 与 Agent 平级且长期并存,分别保留持久化模型与执行链。
|
||||
- 现有 Pipeline 不迁移为 Agent,Pipeline 内的 runner config 不复制到 Agent。
|
||||
- 用户需要 Agent 时新建独立 Agent并选择已安装的 AgentRunner。
|
||||
- 用户需要 Agent 时新建独立 Agent并选择已安装的 Runner。
|
||||
- Host 不按 LocalAgent id 做运行时、Box 或 WebUI 特判。
|
||||
- AgentRunner 的 SDK/Python 与 scoped MCP bridge 回调共享 Host 授权与事件 session 规则。
|
||||
- Runner 的 SDK/Python 与 scoped MCP bridge 回调共享 Host 授权与事件 session 规则。
|
||||
|
||||
## 2. 阶段总览
|
||||
|
||||
| 阶段 | 目标 | 主要仓库 | 完成条件 |
|
||||
| --- | --- | --- | --- |
|
||||
| P0 | SDK 事件、能力与 AgentRunner 协议 | `langbot-plugin-sdk` | typed entities、manifest、proxy、runtime action 通过测试 |
|
||||
| P0 | SDK 事件、能力与 Runner 协议 | `langbot-plugin-sdk` | typed entities、manifest、proxy、runtime action 通过测试 |
|
||||
| P1 | 平台适配器 EBA 化 | LangBot + SDK | 事件转换、能力声明、通用/透传 API 通过 adapter checklist |
|
||||
| P2 | Host 观察者与响应者路由 | LangBot backend | observer 广播 + Pipeline/Agent/discard 单目标仲裁可运行 |
|
||||
| P3 | 独立 Agent 与 Runner 注册 | LangBot backend + plugins | Agent CRUD、registry、run authorization、delivery 可运行 |
|
||||
@@ -32,8 +32,8 @@ EBA 跨越 SDK、平台适配器、LangBot Host、WebUI 与插件生态,按可
|
||||
|
||||
- 定义规范化平台事件、actor/subject/conversation/delivery context。
|
||||
- 定义 adapter `supported_events`、`supported_apis` 与平台透传 API。
|
||||
- 定义 AgentRunner manifest、run context/result、resource handles 和 pull/callback API。
|
||||
- 提供 `AgentRunAPIProxy` 与 SDK-owned scoped MCP bridge。
|
||||
- 定义 Runner manifest、run context/result、resource handles 和 pull/callback API。
|
||||
- 提供 `RunnerAPIProxy` 与 SDK-owned scoped MCP bridge。
|
||||
- 保持协议传输与权限校验可测试,不把 Host 私有 Query 对象暴露给插件。
|
||||
|
||||
### 验收
|
||||
@@ -76,7 +76,7 @@ adapter event
|
||||
|
||||
- Plugin EventListener 是 observer,不作为 priority fallback。
|
||||
- Pipeline 只处理消息事件并复用完整 Stage 链。
|
||||
- Agent 使用独立 Agent 配置和 AgentRunner Host orchestrator。
|
||||
- Agent 使用独立 Agent 配置和 Runner Host orchestrator。
|
||||
- edit/reaction 等事件的 observer 副作用能力按事件和 adapter 能力过滤。
|
||||
- dry-run 与合成派发必须使用同一匹配器,避免 UI 预览与真实路由漂移。
|
||||
|
||||
@@ -86,13 +86,13 @@ adapter event
|
||||
- 同一事件最多一个响应目标,但 observer 仍能收到事件。
|
||||
- Pipeline 与 Agent 可以在同一个 Bot 的不同 binding 中同时生效。
|
||||
|
||||
## 6. P3:独立 Agent 与 AgentRunner
|
||||
## 6. P3:独立 Agent 与 Runner
|
||||
|
||||
### 工作项
|
||||
|
||||
- `agents` 只保存 Agent;Pipeline 继续使用自己的表和 API。
|
||||
- Agent config 使用 `runner.id` 与 `runner_config[runner_id]`。
|
||||
- registry 只展示已安装、有效的插件 AgentRunner。
|
||||
- registry 只展示已安装、有效的插件 Runner。
|
||||
- Host 构造 run-scoped resources、state、delivery 与 event log/transcript。
|
||||
- SDK/Python `call_tool` 和 scoped MCP bridge 都回到同一个 Host ToolManager。
|
||||
- Box session 由 Host 将 instance/workspace/bot/adapter/target/thread scope 规范化并哈希为固定长度 `lb-box-<sha256>`;同 scope 稳定、不同 scope 隔离、缺少 identity 时 fail closed。
|
||||
@@ -117,7 +117,7 @@ adapter event
|
||||
### 验收
|
||||
|
||||
- 页面不出现 LocalAgent 专属 banner、变量隐藏或 Box/Pipeline 注入逻辑。
|
||||
- 空 Runner 市场状态给出可安装 AgentRunner 的正常路径。
|
||||
- 空 Runner 市场状态给出可安装 Runner 的正常路径。
|
||||
- Pipeline Debug Chat/Monitoring 与 Agent 运行日志分别可用。
|
||||
|
||||
## 8. P5:发布门禁
|
||||
@@ -125,7 +125,7 @@ adapter event
|
||||
### 自动化
|
||||
|
||||
- LangBot backend unit/integration tests 与 Ruff。
|
||||
- SDK AgentRunner/proxy/MCP bridge tests。
|
||||
- SDK Runner/proxy/MCP bridge tests。
|
||||
- Web lint/build 与关键 Playwright cases。
|
||||
- `skills/bin/lbs validate`、`skills/bin/lbs index --check`。
|
||||
- LocalAgent 与其他官方 Runner plugin package/test gate。
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
# Agent 与 Pipeline 统一编排(产品最终形态)
|
||||
|
||||
> Implementation update (2026-09-08): the EventListener observer-broadcast proposal below is superseded by [Event processors](09-event-processors.md). Legacy EventListener hooks run only inside Pipeline. New EBA handlers use explicitly created and bound EventProcessor instances, a third peer processor type alongside Agent and Pipeline.
|
||||
> Implementation update (2026-09-08): the EventListener observer-broadcast proposal below is superseded by [Event processors](09-event-processors.md). Legacy EventListener hooks run only inside Pipeline. New EBA handlers use explicitly created and bound Runner instances, a third peer processor type alongside Agent and Pipeline.
|
||||
|
||||
> **状态**:历史方向稿(2026-06-12);2026-09-05 标记归档用途。本文的示意 schema、5.0 发布火车、SDK 0.5.0aX 配套与多租户“预留”描述不再作为实施合同。当前 4.11 产品形态见 [08-agent-page-and-event-orchestration.md](./08-agent-page-and-event-orchestration.md),协议见 [PROTOCOL_V1.md](../agent-runner-pluginization/PROTOCOL_V1.md),已完成与剩余事项见 [STATUS.md](../agent-runner-pluginization/STATUS.md)。保留正文仅用于解释早期设计取舍。
|
||||
>
|
||||
@@ -20,7 +20,7 @@
|
||||
EventRouter(事件 → 处理器绑定)
|
||||
├─→ 选中的处理器(响应者,单一仲裁)
|
||||
│ ├─ Pipeline:保留现有实体和执行链,仅处理消息事件
|
||||
│ └─ Agent:用户新建并选择 AgentRunner 插件,可接本地、低代码或外部 runtime
|
||||
│ └─ Agent:用户新建并选择 Runner 插件,可接本地、低代码或外部 runtime
|
||||
│
|
||||
└─→ 插件 EventListener(观察者,N 个广播,可 prevent_default)
|
||||
```
|
||||
@@ -51,7 +51,7 @@ EventRouter(事件 → 处理器绑定)
|
||||
04 文档中的 pipeline / agent / webhook / plugin 四种 handler_type,本质上都是"对事件作出响应的逻辑",差别只在编写和部署方式。产品层统一展示和绑定这些处理器,但不会把既有 Pipeline 持久化为 Agent:
|
||||
|
||||
- **产品**:用户只需理解"给 Bot 的事件绑定处理器",处理器可以是 Pipeline 或 Agent;
|
||||
- **工程**:路由层按 `target_type` 分发到 Pipeline 或 Agent,Agent 的扩展集中到 AgentRunner 抽象;
|
||||
- **工程**:路由层按 `target_type` 分发到 Pipeline 或 Agent,Agent 的扩展集中到 Runner 抽象;
|
||||
- **生态**:Agent 成为市场上可分发、可复用的一等公民。
|
||||
|
||||
### 2.2 收编映射
|
||||
@@ -59,7 +59,7 @@ EventRouter(事件 → 处理器绑定)
|
||||
| 原 handler_type(04 文档) | 收编后 |
|
||||
|---------------------------|--------|
|
||||
| `pipeline` | 保留 Pipeline 实体;binding 使用 `target_type=pipeline` 和原 `pipeline_uuid`,进程内直接复用 MessageAggregator → QueryPool → Pipeline 机制 |
|
||||
| `agent`(RequestRunner) | 用户新建独立 Agent,并选择对应 AgentRunner 插件;不读取或复制旧 Pipeline 内嵌 runner 配置 |
|
||||
| `agent`(RequestRunner) | 用户新建独立 Agent,并选择对应 Runner 插件;不读取或复制旧 Pipeline 内嵌 runner 配置 |
|
||||
| `webhook` | 外部 Agent 的一种:事件 POST 出去、响应解析为动作(保留 04 §5.4 的请求/响应格式) |
|
||||
| `plugin`(EventListener 分发) | **不收编**——角色不同,见 §2.3 |
|
||||
|
||||
@@ -76,7 +76,7 @@ EventRouter(事件 → 处理器绑定)
|
||||
|
||||
### 3.1 独立 Agent 与现有 Pipeline
|
||||
|
||||
Agent 与 Pipeline 都是一等处理器。用户创建 Agent、选择已安装的 AgentRunner,再把适合的事件绑定到 Agent;Pipeline 继续保存在 Pipeline 表中,以完整 Stage 链处理消息事件。两者可在同一处理器列表中以不同 `kind` 展示和选择;这种聚合展示不会创建额外记录,也不会在两种模型之间复制配置。
|
||||
Agent 与 Pipeline 都是一等处理器。用户创建 Agent、选择已安装的 Runner,再把适合的事件绑定到 Agent;Pipeline 继续保存在 Pipeline 表中,以完整 Stage 链处理消息事件。两者可在同一处理器列表中以不同 `kind` 展示和选择;这种聚合展示不会创建额外记录,也不会在两种模型之间复制配置。
|
||||
|
||||
```python
|
||||
class Agent(Base):
|
||||
@@ -84,7 +84,7 @@ class Agent(Base):
|
||||
uuid: str # 主键
|
||||
name: str
|
||||
kind: str # 固定为 "agent";Pipeline 使用自己的持久模型
|
||||
component_ref: str # AgentRunner id,例如 plugin:<author>/<plugin>/<runner>
|
||||
component_ref: str # Runner id,例如 plugin:<author>/<plugin>/<runner>
|
||||
config: dict # JSON — runner id、runner config 与资源/状态/投递策略
|
||||
# 多租户预留:归属主体字段(tenant/workspace),首版可空
|
||||
```
|
||||
@@ -156,7 +156,7 @@ class AgentChunk:
|
||||
```
|
||||
|
||||
**流式**:复用 SDK 通信协议既有的 `chunk_status: continue/end` 机制,`handle()` 的每次 yield 对应一个 chunk。
|
||||
**Pipeline 与 Agent 分流**:Pipeline target 继续走 LangBot 进程内的 Pipeline 执行链;独立 Agent 经 AgentRunner 插件 runtime 分发。路由层通过 binding 的 `target_type` 明确区分二者。
|
||||
**Pipeline 与 Agent 分流**:Pipeline target 继续走 LangBot 进程内的 Pipeline 执行链;独立 Agent 经 Runner 插件 runtime 分发。路由层通过 binding 的 `target_type` 明确区分二者。
|
||||
|
||||
### 4.3 执行语义与可靠性
|
||||
|
||||
@@ -173,7 +173,7 @@ class AgentChunk:
|
||||
| 版本 | 内容 | 备注 |
|
||||
|------|------|------|
|
||||
| 4.11(可选) | 现状成果:12 个 EBA 适配器、插件全事件订阅、`call_platform_api` | 对用户不可见的管道工程 + 插件新能力,不动产品概念 |
|
||||
| **5.0** | 产品形态首发:EventRouter + event→处理器绑定 + WebUI 编排 + 旧 Bot 路由迁移 + 独立 Agent / AgentRunner 插件 + SDK Agent 组件契约(可标 experimental) | `use_pipeline_uuid` 仅改写为指向原 Pipeline 的 binding,不生成 Agent;配 SDK 0.5.0 正式版;走 beta 周期 |
|
||||
| **5.0** | 产品形态首发:EventRouter + event→处理器绑定 + WebUI 编排 + 旧 Bot 路由迁移 + 独立 Agent / Runner 插件 + SDK Agent 组件契约(可标 experimental) | `use_pipeline_uuid` 仅改写为指向原 Pipeline 的 binding,不生成 Agent;配 SDK 0.5.0 正式版;走 beta 周期 |
|
||||
| 5.x | 工作流 Agent(工作流引擎线挂入)、Agent 市场生态、剩余适配器(satori 等)、Agent 插件化收尾 | 验证开放注册机制 |
|
||||
| 多租户 | 独立评估:仅数据隔离 → 5.x 部署选项;伴随权限/计费/产品定位变化 → 6.0 | 前置条件是 §4.3 的归属主体预留已落实 |
|
||||
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
# 处理器页面与事件编排产品设计
|
||||
|
||||
> Implementation update (2026-09-08): the EventListener observer-broadcast proposal below is superseded by [Event processors](09-event-processors.md). Legacy EventListener hooks run only inside Pipeline. New EBA handlers use explicitly created and bound EventProcessor instances, a third peer processor type alongside Agent and Pipeline.
|
||||
> Implementation update (2026-09-08): the EventListener observer-broadcast proposal below is superseded by [Event processors](09-event-processors.md). Legacy EventListener hooks run only inside Pipeline. New EBA handlers use explicitly created and bound Runner instances, a third peer processor type alongside Agent and Pipeline.
|
||||
|
||||
> 状态:当前实现说明(2026-09-05),对应 `dev/4.11.x`。P0–P3 已集成;发布验收见 [STATUS.md](../agent-runner-pluginization/STATUS.md)。
|
||||
>
|
||||
@@ -12,7 +12,7 @@ LangBot 的处理逻辑分成两种同级形态:
|
||||
|
||||
| 形态 | 定位 | 可处理事件 | 典型用户 |
|
||||
| --- | --- | --- | --- |
|
||||
| Agent | runner 驱动的事件优先处理器,承载 AgentRunner / 外部 runner | `message.*`、`group.*`、`friend.*`、`bot.*`、`feedback.*`、`platform.*` 等声明范围 | 需要直接处理多类平台事件或接入外部 agent runtime 的用户 |
|
||||
| Agent | runner 驱动的事件优先处理器,承载 Runner / 外部 runner | `message.*`、`group.*`、`friend.*`、`bot.*`、`feedback.*`、`platform.*` 等声明范围 | 需要直接处理多类平台事件或接入外部 agent runtime 的用户 |
|
||||
| Pipeline | 可视化、可控、可组合的消息处理流水线,执行完整 Stage 链 | 仅 `message.*`,首版等价于 `message.received` | 需要预处理、AI、后处理、扩展和输出控制的消息场景 |
|
||||
|
||||
处理器页面负责统一管理这两种处理单元:
|
||||
@@ -38,7 +38,7 @@ LangBot 的处理逻辑分成两种同级形态:
|
||||
- Pipeline:沿用原 Pipeline 配置页,包括 AI、触发、安全、输出、扩展、Debug、Monitoring;
|
||||
- Agent:基础信息由详情入口编辑,主配置分为运行器、运行器配置、事件与工具;事件范围、自动事件工具、平台级动作和普通工具白名单在同一配置流程内维护。
|
||||
|
||||
处理器详情复用 `ProcessorDetailWorkbench`;Agent 与 Pipeline 保留各自的配置、调试和日志语义。`AgentRunnerSelect` 提供已安装 Runner 和市场安装入口,安装状态可恢复;Runner 配置来自动态 metadata,不按 LocalAgent id 定制 Host 表单。调试事件选择位于输入区域;Bot 的平台事件调试位于机器人配置中,路由 dry-run 只解释匹配结果。
|
||||
处理器详情复用 `ProcessorDetailWorkbench`;Agent 与 Pipeline 保留各自的配置、调试和日志语义。`RunnerSelect` 提供已安装 Runner 和市场安装入口,安装状态可恢复;Runner 配置来自动态 metadata,不按 LocalAgent id 定制 Host 表单。调试事件选择位于输入区域;Bot 的平台事件调试位于机器人配置中,路由 dry-run 只解释匹配结果。
|
||||
|
||||
`/home/pipelines` 继续提供 Pipeline 直接编辑路径;共享处理器入口当前使用 `/home/agents`。URL 是实现路径,不代表 Agent 包含 Pipeline。
|
||||
|
||||
@@ -174,8 +174,8 @@ Bot 使用 `event_bindings` JSON 字段持久化路由。当前未引入独立
|
||||
|
||||
- EBA 事件先广播插件 observer。
|
||||
- 然后按 `event_bindings` 的事件模式、filters、priority 和顺序选择一个处理器。
|
||||
- Pipeline 目标通过 MessageAggregator 进入完整 Pipeline Stage 链;Agent 目标直接进入 AgentRunner 链路。
|
||||
- 非消息事件只选择声明支持该事件的 Agent,不调用 Pipeline;AgentRunner 输出有平台 reply target 时会投递回平台。
|
||||
- Pipeline 目标通过 MessageAggregator 进入完整 Pipeline Stage 链;Agent 目标直接进入 Runner 链路。
|
||||
- 非消息事件只选择声明支持该事件的 Agent,不调用 Pipeline;Runner 输出有平台 reply target 时会投递回平台。
|
||||
|
||||
## 7. 不做的事
|
||||
|
||||
|
||||
@@ -1,30 +1,18 @@
|
||||
# Event processors and Pipeline plugin compatibility
|
||||
|
||||
Status: implemented in the 4.11 development branches of LangBot and the Plugin SDK,
|
||||
2026-09-08. The Host uv configuration pins the matching SDK commit. Deploy both
|
||||
revisions together; older SDK releases do not contain this component. Switch the
|
||||
development source pin to a published SDK release before a stable PyPI release.
|
||||
This design supersedes the automatic EBA EventListener observer broadcast in
|
||||
the earlier EBA documents. Existing Pipeline plugin behavior remains supported.
|
||||
# Runner components and Pipeline plugin compatibility
|
||||
|
||||
## Product boundary
|
||||
|
||||
Three processor types appear together in the Processors area:
|
||||
| Product | Implementation | Event entry |
|
||||
| --- | --- | --- |
|
||||
| Pipeline | Pipeline stages and an agent-capable Runner | Received messages |
|
||||
| Agent | A Runner with `spec.usages: [agent]` | Configured events |
|
||||
| Plugin processor | A Runner with `spec.usages: [event]` | Events declared in `spec.events` |
|
||||
|
||||
| Product | Implementation | Event entry | Flow ownership |
|
||||
| --- | --- | --- | --- |
|
||||
| Pipeline | Existing Pipeline stages and configuration | Received messages | Pipeline stages, including legacy plugin hooks |
|
||||
| Agent | A configured plugin AgentRunner | Supported EBA events | The selected runner |
|
||||
| Event processor | A configured plugin EventProcessor | Supported EBA events | Plugin Python handlers |
|
||||
|
||||
Use **Event processor** as the product label and **EventProcessor** as the SDK
|
||||
component name. The localized description should explain that the plugin defines
|
||||
the processing logic. It must not suggest an LLM, prompt, or visual workflow is
|
||||
required.
|
||||
|
||||
An installed component is a reusable implementation. A processor instance is a
|
||||
user-created configuration of that component. A Bot event binding selects an
|
||||
instance, not an installed plugin package directly.
|
||||
Runner is the only component for these execution styles. `spec.usages` can contain
|
||||
both `agent` and `event`; these are selection capabilities, not mutually exclusive
|
||||
execution modes. An installed component is reusable code. Users create processor
|
||||
instances, select a Runner and configure it, then bind Bot events to the instance.
|
||||
Installation alone never subscribes a component to incoming events.
|
||||
|
||||
## Legacy EventListener contract
|
||||
|
||||
@@ -57,168 +45,48 @@ information must be distinguished from fields that were dropped during conversio
|
||||
Direct Agent and Event processor execution must not synthesize Pipeline lifecycle
|
||||
hooks. Those hooks describe actual Pipeline stages.
|
||||
|
||||
## EventProcessor SDK contract
|
||||
## SDK and runtime
|
||||
|
||||
Introduce a distinct component kind instead of changing what an existing
|
||||
EventListener manifest means. One package may contain both kinds; only the legacy
|
||||
EventListener participates in Pipeline hook dispatch.
|
||||
`lbp comp Runner` generates `components/runner`. Every component uses
|
||||
`plugin:author/plugin/name` as its identity. Names are unique within a plugin.
|
||||
The component can override `async run(ctx)` and yield RunnerResult objects, or
|
||||
register typed platform callbacks through `@self.handler(EventClass)` in
|
||||
`initialize()`. Default run dispatches an exact handler, falling back to EBAEvent.
|
||||
A custom run can delegate to this dispatch with `await super().run(ctx)`.
|
||||
|
||||
Retain the familiar authoring shape:
|
||||
Both styles share RunnerContext, invocation-bound ctx.api, logs, replies, deadlines,
|
||||
cancellation, worker isolation and the run ledger. ctx.event is the envelope;
|
||||
ctx.platform_event is the typed platform payload. Each invocation owns its context;
|
||||
never put the current context or run ID on a shared component or plugin instance.
|
||||
|
||||
```python
|
||||
from langbot_plugin.api.definition.components.event_processor import EventProcessor, EventProcessorContext
|
||||
from langbot_plugin.api.entities.builtin.platform.events import MemberJoinedEvent
|
||||
class WelcomeProcessor(EventProcessor):
|
||||
async def initialize(self):
|
||||
await super().initialize()
|
||||
The runtime emits completion on normal return unless the Runner already emitted a
|
||||
terminal result. Exceptions fail the run and retain preceding results. Cancelling
|
||||
the result stream cancels execution. There is no implicit retry or hidden model
|
||||
loop. Returned text and logs do not send platform messages: replies are explicit
|
||||
ctx.reply / ctx.reply_stream actions. Pipeline retains its configured output stage.
|
||||
|
||||
@self.handler(MemberJoinedEvent)
|
||||
async def on_join(ctx: EventProcessorContext):
|
||||
await ctx.reply(f"Hello, {ctx.event.member.nickname}")
|
||||
```
|
||||
`self.plugin` continues to expose ordinary plugin APIs. ctx.api carries run-scoped
|
||||
resource grants and records tool actions. Workspace and installation authorization
|
||||
remain Host-enforced. Run identity and API operation scope are separate concepts.
|
||||
|
||||
Handlers receive typed EBA events directly. Do not maintain a second, incomplete
|
||||
mapping into plugin-only EBA wrapper classes. Preserve complete public event
|
||||
fields; compact log previews must not become the execution payload. Include the
|
||||
generic platform-specific event contract for adapter-specific events.
|
||||
## Selection and observability
|
||||
|
||||
The context belongs to one invocation and exposes the event, processor/run
|
||||
identifiers, instance configuration, logging, and authorized Host APIs. It has no
|
||||
fabricated Pipeline Query. Reuse Host run tracking, deadlines, installation
|
||||
authority, platform capabilities, and delivery records where appropriate.
|
||||
Both product selectors discover the same Runner catalog and filter by usage.
|
||||
Validate usage again before execution. Event-capable Runners must declare events;
|
||||
users can route a subset, but cannot expand the manifest capability. Unconfigured
|
||||
instances expose no event subscriptions. Workspace ownership, plugin scope and
|
||||
instance identity are checked for routing, execution, cancellation and run reads.
|
||||
|
||||
A handler returning normally completes its invocation. There is no implicit LLM
|
||||
loop, automatic second processor, or hidden retry of side effects. An exception
|
||||
marks the run failed and retains the associated log. New processing handlers do
|
||||
not use prevent_default to control another processor; routing has already chosen
|
||||
the current processor. The legacy methods keep their existing Pipeline meaning.
|
||||
Plugin processor details keep event debugging on the left and configuration/logs
|
||||
on the right. Component settings use the existing schema form. Logs and action
|
||||
results remain distinct from actual platform delivery; debug delivery is Mock.
|
||||
Agent-native interactions stay on the Agent product path; typed handlers consume
|
||||
platform events. Legacy Pipeline lifecycle hooks remain on the Pipeline path.
|
||||
|
||||
## Activation and routing
|
||||
## Validation
|
||||
|
||||
The activation sequence is explicit:
|
||||
|
||||
1. Install a plugin containing an EventProcessor component.
|
||||
2. Create an Event processor in the Processors area.
|
||||
3. Open its detail page, select a plugin component, and save its configuration.
|
||||
4. Bind a Bot event to that processor instance in the existing event routing UI.
|
||||
|
||||
Installation and processor creation alone do not subscribe to Bot events.
|
||||
The component declares the event types it handles; Bot bindings select the subset
|
||||
of supported events to deliver. One package may supply multiple components, and
|
||||
multiple instances may use the same component with independent configuration.
|
||||
|
||||
Extend the existing single-target route arbitration with `event_processor`.
|
||||
There is no automatic EBA broadcast to installed EventListeners. Keep Pipeline hook dispatch inside the Pipeline path. Existing observer
|
||||
plugins must explicitly adopt the new component and be bound by the user; do not
|
||||
create subscriptions during migration.
|
||||
|
||||
An unconfigured instance has no supported events and cannot execute. Validate
|
||||
component availability, event compatibility, Workspace ownership, and instance
|
||||
identity when configuring the instance and again at invocation. A disabled or
|
||||
unavailable plugin leaves the instance visible with an actionable unavailable
|
||||
status. It must not silently fall back to Agent or Pipeline.
|
||||
|
||||
## Compact UI
|
||||
|
||||
Creation adds a third type next to Agent and Pipeline and asks only for basic
|
||||
instance information. Select the plugin component in the detail-page header.
|
||||
Show component-defined configuration in the right pane, with Configuration and
|
||||
Logs tabs. Keep unsaved values when switching tabs, and open Logs after a debug
|
||||
run finishes. The component selector remains in the page header.
|
||||
If no component is installed, show a relevant plugin installation entry point;
|
||||
installing still does not create a binding.
|
||||
|
||||
The detail page keeps event debugging on the left while the right pane switches
|
||||
between configuration and logs. A compact run list shows event type, time, status and known
|
||||
processing duration. Selecting a row shows that run's identity, input, logs,
|
||||
actions and outcome below. There is no shared timeline between unrelated runs.
|
||||
The additive `created_at_ms`, `started_at_ms`, and `finished_at_ms` fields retain
|
||||
Host lifecycle precision for elapsed-time display.
|
||||
Keep payloads and error details collapsed until expanded. Distinguish attempted
|
||||
delivery from confirmed delivery and display the actual destination.
|
||||
|
||||
Place component identity, availability, bindings, and configuration in a compact
|
||||
secondary area. Do not add a prompt editor, model selector, or flow designer.
|
||||
The plugin implements the processing flow in code.
|
||||
|
||||
## Delivery sequence and acceptance
|
||||
|
||||
1. Repair and regression-test Pipeline EventContext handling and legacy payload
|
||||
conversion independently of the new processor feature.
|
||||
2. Add the SDK component, context, manifest/scaffolding, and explicit invocation
|
||||
contract; verify registration, event coverage, and process isolation.
|
||||
3. Add Host instance management, event routing, execution tracking, and matching
|
||||
HTTP/MCP/skill surfaces. Turn off automatic EBA observer dispatch in this step.
|
||||
4. Add creation, binding, availability, logs, and delivery trace UI with i18n.
|
||||
5. Exercise a real packaged plugin through installation, explicit instance
|
||||
creation, Bot binding, invocation, logging, and reply delivery.
|
||||
|
||||
Acceptance must prove that installation alone invokes no handlers; one matching
|
||||
binding invokes exactly the chosen component; instance configuration and run
|
||||
history remain separate; all declared EBA events retain their fields; unavailable
|
||||
components fail visibly; and legacy plugins keep the documented Pipeline hook
|
||||
order and behavior. Unit tests alone do not establish a successful live plugin
|
||||
installation or platform delivery.
|
||||
|
||||
|
||||
## Implemented transport and APIs
|
||||
|
||||
`lbp comp EventProcessor` scaffolds a component in `components/event_processor`.
|
||||
Its manifest uses `kind: EventProcessor` and `spec.events`, for example
|
||||
`[group.member_joined]`. `spec.config` defines instance parameters. A component
|
||||
that calls `ctx.reply()` declares `spec.permissions.tools: [detail, call]`.
|
||||
|
||||
References use `event_processor:author/plugin/component`, separate from
|
||||
`plugin:author/plugin/runner`. Both kinds share the existing run transport,
|
||||
installation authorization, deadlines and run ledger. The trusted Host selects
|
||||
the component kind; the worker invokes only that exact kind and name.
|
||||
There is no model invocation in the EventProcessor base class.
|
||||
|
||||
`EventProcessorContext` provides `event`, `run_id`, `config`, `api`, `log()` and
|
||||
`reply()`. `api` is the existing run-scoped Host proxy. Use `ctx.config` for instance
|
||||
parameters; plugin installation configuration remains separate. Handlers may
|
||||
register the `EBAEvent` base class as a catch-all. An exact typed handler takes
|
||||
precedence over that fallback. Multiple handlers for the same type run in their
|
||||
registration order, within one invocation.
|
||||
|
||||
HTTP instance management uses `/api/v1/agents` with `kind: event_processor`.
|
||||
Metadata at `/api/v1/agents/_/metadata` lists installed `event_processors`.
|
||||
Creation accepts `component_ref` and `parameters`; the Host derives the supported
|
||||
event patterns from the component. Bot bindings use `target_type: event_processor`
|
||||
and the created instance UUID as `target_id`.
|
||||
|
||||
- `GET /api/v1/agents/{id}/runs?before_id=...` lists this instance's runs.
|
||||
- `GET /api/v1/agents/{id}/runs/{run_id}/events?after_sequence=...` pages its logs
|
||||
and action results. A run from another instance or Workspace is rejected.
|
||||
- The corresponding MCP tools are `get_processor_metadata`, `list_processor_runs`
|
||||
and `get_processor_run_events`, alongside processor CRUD.
|
||||
- `/api/v1/agents/{id}/debug` accepts a full typed EBA event in `data`. Platform
|
||||
actions use Mock; other authorized tools retain their configured behavior.
|
||||
|
||||
The detail page polls run updates, keeps payload details collapsed and separates
|
||||
logs from platform delivery. Completed handlers produce no synthetic reply text.
|
||||
|
||||
|
||||
## Verification (2026-09-08)
|
||||
|
||||
- SDK API, scaffolding and Plugin Runtime suites: 684 passed.
|
||||
- Host runner, service, controller, MCP and adapter regression suites: 971 passed.
|
||||
- Pipeline and registry regression suites: 243 passed, one environment-dependent skip.
|
||||
- Frontend unit suite: 74 passed; TypeScript and changed-file lint checks passed.
|
||||
- Real packaged-plugin tests cover installation, component-kind separation,
|
||||
invocation, mock platform delivery, instance isolation and persisted logs.
|
||||
- Authenticated Edge testing created an instance and a loopback OneBot bot, saved
|
||||
a member-join binding, injected one native notice and received exactly one
|
||||
`send_group_msg` response. The detail page displayed the completed run,
|
||||
localized action name, destination and returned message ID. No external IM
|
||||
account or live model was involved.
|
||||
- Browser regression covers expanding long payloads, reaching the last log and
|
||||
pagination without duplication. Eight unrelated existing browser failures were
|
||||
reproduced against the pre-change commit; the full suite is not green.
|
||||
- Repository-wide lint also retains the pre-existing duplicate `send_image_msg`
|
||||
in the WeCom customer-service library and existing formatting failures outside
|
||||
this change. The i18n check has the same pre-existing diagnostics as its baseline.
|
||||
|
||||
Native Agent interaction-resumption is not enabled for EventProcessor bindings;
|
||||
its input contract is the platform EBA event collection, not a synthetic Agent
|
||||
continuation. Plugins should handle platform events through their typed handlers.
|
||||
SDK tests cover both execution styles, event matrices, concurrent contexts,
|
||||
termination, cancellation and permissions. Packaged CLI tests generate, build and
|
||||
execute the published component. Core tests cover usage-filtered discovery, event
|
||||
routing, Workspace authorization and real plugin-runtime transport. RunnerDemo
|
||||
provides multi-step actions, configuration isolation and controlled failures.
|
||||
|
||||
Reference in New Issue
Block a user