# sundynix-agentix · 架构设计文档（当前完整版）

> 版本：2026-07-02（反映 T0–T2 全量 + T4.B/E 完成 + T4.F 部分后的现状）
> 定位：**事件驱动的 AI Agent 平台**。以 NATS 为统一总线，服务经契约解耦，Eino 为编排核心，控制面热切换。
> 配套文档：`ARCHITECTURE_REVIEW.md`（架构评审：优缺点/技术债）、`DEPTH_ROADMAP.md`（路线图）、`EINO_ADOPTION.md`（Eino 采纳）。

---

## 1. 系统概述

sundynix-agentix 把「用户在画布上编排 Agent 图 → 平台调度执行 → 实时回流结果」做成一套可运维、可观测、可扩展的平台。核心特征：

- **图编排执行**：前端画布导出 DSL（节点+连线），后端编译为可执行图，支持分支、并行、多智能体、人工审批。
- **工具即服务**：能力（RAG/记忆/历史/报告/沙箱）以独立 MCP 服务经 NATS 暴露，加工具零改调度代码。
- **分层韧性**：模型 failover + 熔断 + 预算 + 输入护栏 + 输出脱敏 + 自动评测纠偏（「恒温器」治理层）。
- **控制面热切换**：模型配置、提示词经 NATS 广播热下发，不重启即生效。
- **流式原生**：token 流与执行轨迹经 NATS→Redis Stream→SSE 实时回流，支持断点重放。

---

## 2. 分层架构总览

```
┌── 客户端层 ───────────────────────────────────────────────┐
│  桌面端 Wails(:5173，用户工作产品)   管理端 React(:5174，运维控制台) │
└──────────────┬───────────────────────────┬────────────────┘
               │ HTTP / SSE                 │ HTTP
┌── 接入层 ─────┴───────────────────────────┴────────────────┐
│  gateway (gin, :8080)                                        │
│  JWT鉴权 · 路由 · 输入护栏 · 限流(按用户) · 审计 · SSE回流 · 导出  │
└──────────────────────────┬─────────────────────────────────┘
                           │
┌── 总线层 ─────────────────┴─────────────────────────────────┐
│  NATS + JetStream ——「万物总线」                              │
│  任务 · 工具RPC · token流 · 执行轨迹 · 控制面广播 · 心跳 · 持久队列 │
└──┬──────────────────────┬──────────────────────┬────────────┘
   │                      │                      │
┌──┴────────┐    ┌────────┴────────┐    ┌────────┴────────┐
│ dispatcher │    │     mcp-go       │    │     mcp-py       │
│ 编排核心    │    │ Go I/O 工具服务   │    │ Python 算法工具  │
│ Eino+harness│    │ RAG/记忆/历史/报告│    │ 沙箱/解析        │
└──┬────────┘    └────────┬────────┘    └─────────────────┘
   │ LLM providers          │
   │ (OpenAI 兼容)           │
┌──┴────────────────────────┴─────────────────────────────────┐
│ 数据层：PostgreSQL(关系) · Redis(缓存/流/限流) · Milvus(向量)      │
│         Neo4j(图谱) · MinIO(对象/正文) · Jaeger(OTel 追踪)         │
└──────────────────────────────────────────────────────────────┘
```

**分层原则**：服务间**互不 import**，只依赖 `shared/contract`（数据契约）+ `shared/bus`（NATS 封装）。任何跨服务通信都过 NATS。

---

## 3. 组件详细设计

### 3.1 gateway（接入层，gin）
唯一对外 HTTP 入口，不含业务编排。职责：
- **鉴权**：JWT 无状态（`owner` = 雪花 user.id）；`RequireAuth`（登录）/ `RequireAdmin`（管理面，白名单 `ADMIN_USER_IDS`）。
- **中间件链**（顺序）：Recovery → OTel → RequestID → Observe(指标+日志) → CORS → **Auth** → **RateLimit(按 uid，未认证按 IP)** → **Guardrail(输入护栏+命中落库)**。
- **DSL 拓扑校验**：`ParseAndAssemble` 前置拦截重复/空节点 id、悬挂边（防坏图进编排后被 compose 静默跳过）。
- **SSE 回流**：`/tasks/:id/stream`(token 流)、`/tasks/:id/exec`(执行轨迹)、`/kb/ingest/:id/stream`(入库进度)；优先读 Redis Stream（可断点续传），降级 live NATS。
- **报告导出**：`/reports/:id/export?format=docx|md` → 经 NATS 调 mcp-go 现渲染 → `c.File` 流回。
- **控制面 API**（`/admin/*`，RequireAdmin）：模型 CRUD、计价、系统状态探活、系统聚合 overview、审计流、护栏事件流。
- **审计**：`middleware.Audit(db)` 对变更类请求（POST/PUT/DELETE）best-effort 落库。

### 3.2 dispatcher（编排核心）
消费 NATS 任务，用 Eino 执行编排图 + harness 治理。详见 §5、§6。

### 3.3 mcp-go（Go 工具服务）
MCP 协议端点，订阅 `sundynix.tools.go.>`（queue group `mcp-go-workers`）。工具注册表是**单一事实源**（每工具声明 `cn/desc/agent/params/inject/handler`）：
- **RAG**：`kb_search`(三路混合) / `wiki_search` / `kb_graph` / `kb_ingest` / `kb_delete`(级联删)。三路 = Milvus 向量 + Bleve 全文(落盘) + Neo4j 图谱，RRF 融合 + rerank。
- **记忆**：`memory_get/upsert/delete/list`（用户长期偏好，软删）。
- **历史**：`history_get/append`（会话历史，Redis）。
- **报告**：`report_store`(存源) / `report_render`(渲染 docx 落盘) / `report_export`(按需导出)。
- **元工具**：`list_tools`(自省，供 dispatcher 动态发现) / `health`(Milvus/Neo4j 就绪)。

### 3.4 mcp-py（Python 算法工具）
订阅 `sundynix.tools.py.>`。承载 CPU 密集/生态依赖的算法：沙箱代码执行、文档解析等。**注：算法层目前为桩，调用链路已做真。**

### 3.5 shared（跨服务共享库）
- **bus**：NATS/JetStream 封装（Publish/Subscribe/Request-Reply、控制面广播、心跳、持久队列）。
- **contract**：Task/ToolCall/ToolResult/ModelConfig/报告路径 等跨服务契约。
- **prompts**：提示词注册表（内置默认 + 运行期覆盖）。
- **secrets**：API Key AES-256-GCM 端到端加密（`SUNDYNIX_SECRET_KEY` 三服务须一致）。
- **otel**：OTel 初始化（NATS 跨总线传播 traceparent）。

---

## 4. NATS 总线设计（架构中枢）

NATS 不只是消息队列，而是承载 **5 类通信**：

| 类型 | 模式 | Subject / 机制 | 用途 |
|---|---|---|---|
| 任务提交 | Publish | `sundynix.tasks.*` | gateway → dispatcher |
| 工具调用 | Request-Reply | `sundynix.tools.go.<tool>` / `.py.<tool>` | dispatcher/gateway → mcp-*（queue group 负载均衡） |
| token 流 | Publish/Sub | `sundynix.streams.<task_id>` | dispatcher → gateway → SSE |
| 执行轨迹 | Publish/Sub | exec 事件 | 运行·观测面板 |
| 控制面广播 | Publish | 模型配置 / 提示词激活集 | 热下发 dispatcher/mcp-go（不重启） |
| 心跳探活 | Request-Reply | `sundynix.health.dispatcher` 等 | 管理端服务状态 |
| 持久队列 | JetStream | 入库工作队列（durable consumer） | 崩溃重投 / 幂等 / 背压 / AckWait 续租 |

**⚠️ 运维要点**：单点 NATS（集群为 T3）；本地开发禁止同时开 `devnats` 与 docker NATS（会脑裂）。

---

## 5. 编排引擎设计（Eino compose）

**Eino 只在 dispatcher 里用，是编排引擎地基。**

### 5.1 DSL → compose 图
前端画布导出 `{version, nodes[{id,kind,label,config}], edges[{source,target,sourceHandle}]}`，dispatcher 编译为 Eino `compose.Graph`（`compose_compiler.go`），支持拓扑 + 连线 + 分支剪枝 + DAG 并行调度。**自研 graph.go 解释器已退役，单 compose 引擎。**

### 5.2 节点类型（执行器）
- `input`：用户输入
- `retriever`：RAG 检索（Eino Retriever 包 mcp-go `kb_search`）
- `agent`：模型流式推理（拼消息 → token 流）
- `tool`：调 MCP 工具（编排直连 NATS）
- `branch`：条件路由（true/false 边标签 + **default/else 兜底** + 未匹配收口 END）
- `map`：并行 fan-out（有界并发撰写；**子项失败传播 + 全失败置 fatalErr**）
- `coordinator`：多智能体（专家=agent-as-tool，lead 分解→定制简报→并行派发→综合；**专家超时跳过**）
- `approval`：HITL 人工审批中断（暂停→waiting→批准回 running / 拒绝 rejected，checkpoint 落盘）

### 5.3 ReAct 自主调用（`agent:true` 工具）
`agentTools()` 经 `list_tools` 动态发现 mcp 工具 → 包成 Eino `InvokableTool`（`mcpTool`）→ 模型 function-calling → ToolsNode 分发 → `InvokableRun` 转 NATS RPC。运行时注入 `user_id/session_id/kb`（不暴露给模型）。**加工具只改 mcp-go 注册表，dispatcher 零改动。**

### 5.4 harness 治理层（「恒温器」）
- **评测**：综合分（规则+LLM质量+RAG忠实度）+ 分级（ok/warn/poor），低分**自动纠偏**重生成。
- **输入护栏**：注入检测（网关 Tier1）+ LLM 分类器（dispatcher Tier2 灰区裁决）。
- **输出脱敏**：有状态流式脱敏（跨分片缓冲，杜绝密钥被切断漏检）。
- **预算**：单任务 token 计量 + 封顶（默认 `TASK_TOKEN_BUDGET`，触顶中止全图）。
- **熔断**：后端连续失败→断开→冷却半开探测→恢复（编排层门控 + **model 层每模型熔断**）。

---

## 6. LLM 接入设计

- **接入策略**：开发期接第三方在线 API（OpenAI 兼容），不拉本地 Ollama（但支持 Ollama/vLLM 占位 key）。
- **LLM Pool**（`llm/pool.go`）：经 Eino ChatModel 组件；配置热更新、降级桩（未配置时）。
- **Failover 链**（`llm/failover.go`）：active=主 + 其余=按序备用，串成 `ToolCallingChatModel`，compose/ReAct/Chat 全路径透明。**每模型带熔断器**：主持续失败→熔断→跳过主直连备用；冷却半开探测自动恢复；`WithTools` 重包共享 breakers。
- **输出缓存**（`llm/cache.go`）：包在 failover 外层，缓存 Generate（非流式），键=模型+工具+消息哈希。
- **控制面热切换**：admin 改模型 → gateway 写 DB → NATS 广播 → dispatcher `SetConfig` 热重建 pool。

---

## 7. 数据存储设计

| 存储 | 角色 | 关键内容 |
|---|---|---|
| **PostgreSQL** | 关系事实源 | 用户/任务/评测/模型/计价/提示词/知识库元/文档/双链/编排/审计/护栏事件（表名 `sundynix_` 前缀，AutoMigrate） |
| **Redis** | 缓存/流/限流 | token 用量计数、限流、会话历史、Redis Stream（token/exec 回放） |
| **Milvus** | 向量库 | 文档向量（语义检索），键 file_id |
| **Neo4j** | 图数据库 | 知识图谱三元组（实体 kb+name 共享，关系打 file_id） |
| **MinIO** | 对象存储 | 文档正文（大文件正文一律落 MinIO） |
| **Jaeger** | 追踪 | OTel span（节点/工具/LLM，NATS 跨总线传播） |

**大文件入库生产化**：正文 MinIO + 切片 + 向量并发分批 + 图谱窗口化 + **JetStream 持久工作队列**（崩溃重投/幂等/背压），全 live 验证。

---

## 8. 关键数据流

**① 任务生命周期**：桌面端 POST DSL → gateway 解析+拓扑校验 → NATS `tasks.*` → dispatcher 编译 compose 图执行 → token 流 + 轨迹经 NATS→Redis Stream→SSE 回流 → FSM 状态机落库（submitted/running/done/failed/timeout/waiting/rejected）。

**② 工具调用（两条路）**：
- 编排直连：`o.tools.CallTool()` 直接 NATS→mcp-go（报告写文件走这条，**绕开 Eino**）。
- Eino ReAct：模型 function-call → ToolsNode → `mcpTool.InvokableRun` → NATS→mcp-go。
- 真正执行永远在 mcp-*；**Eino 把工具当黑盒（吃 JSON→吐字符串），不碰文件系统**。

**③ 控制面热切换**：admin 改配置 → gateway 写 DB → NATS 广播激活集 → dispatcher/mcp-go `ApplyOverrides` 热更新。

**④ 报告导出/写文件**：mcp-go `report_render` `os.WriteFile` 到 `SUNDYNIX_REPORTS_DIR`(默认 `$TMPDIR/sundynix-reports/{id}.docx`) → gateway `c.File(路径)` 流回 → 桌面端 Wails `SaveReportAs` 原生另存为落盘。**mcp-go 写、gateway 读须共享该目录。** PDF 目前靠前端打印（无后端 PDF 渲染）。

---

## 9. 安全与治理

- **鉴权**：JWT 无状态；owner 隔离（`owner_id`，单租户假设）。
- **API Key 加密**：AES-256-GCM 端到端密文（PG + NATS 均密文）。
- **输入护栏**：Tier1 正则/黑名单（网关，命中即拦 + 落库 `guardrail_event`）+ Tier2 LLM 分类（dispatcher 灰区）。
- **审计**：敏感操作（改模型/密钥/激活 prompt/审批）经 `audit_log` 留痕，`/admin/audit` 可查。
- **限流**：按登录用户（未认证按 IP），Redis 会话级。
- **CORS**：开发 `*`，生产未显式配置则不放行任意源。

---

## 10. 可观测性

- **OTel 全链路**：节点/工具/LLM span，NATS 跨总线传播 traceparent，Jaeger（:16686）看瀑布。
- **执行轨迹**：ExecEvent → 前端"运行·观测"面板（工具/专家调用、分支决策、审批等）。
- **管理端**：`/status`（基建+服务探活+MCP 工具注册）、`/dashboard`（系统级 overview）、`/audit`（审计+安全事件）。
- **缺口（待补）**：failover/熔断的**运行时态**只在日志、admin UI 不可见（T4.F 🔴）。

---

## 11. 前端设计

**双前端，严格独立、绝不合并**：
- **桌面端**（Wails 原生窗口 + React）：用户工作产品——画布编排/任务运行/知识库/报告/记忆。含 Wails Go 绑定（`app.go`）提供原生能力：另存为/系统应用打开/文件读写/通知。
- **管理端**（React，Vite）：运维控制台——模型/计价/数据源/提示词/服务状态/评测/租户/护栏/审计。已接 vitest。

---

## 12. 部署形态与配置

- **基建**：docker compose（PG/Redis/NATS/Milvus+etcd+MinIO/Neo4j/Jaeger）。
- **应用**：Go 服务本地编译二进制 / `go run`；启动序 = gateway → dispatcher/mcp-go（mcp-go 必须在 Milvus 后）→ mcp-py。
- **关键配置对齐**（多进程/多机须一致）：`SUNDYNIX_SECRET_KEY`、`NATS_URL`、`POSTGRES_DSN`、`SUNDYNIX_REPORTS_DIR`；`ADMIN_USER_IDS`、`CORS_ALLOW_ORIGIN`（生产）、`TASK_TOKEN_BUDGET`、`RATE_LIMIT_PER_MIN` 等。

---

## 13. 当前能力矩阵（干到哪一步）

**✅ 已建（live 验证）**
编排引擎（compose 单引擎，分支/并行/HITL）· 多智能体协调 · RAG 三路混合 + 评测台 · 大文件入库生产化（MinIO+JetStream）· 模型 failover + 每模型熔断 · 输出缓存 · 评测纠偏闭环 · 输入护栏 + 输出脱敏 + 预算 · prompt 版本化 + DB 控制面热切换 · API Key 加密 · OTel 全链路 · **审计可溯源（audit_log + guardrail_event + admin 审计页）** · **系统级 admin overview** · **DSL 拓扑校验** · admin 控制台（含 vitest）

**🔶 进行中（T4.F 健壮性收口）**
拆残骸/CORS/限流已做；**剩** KB 级联删事务化 · 关键 DB 写失败上浮 5xx · 审批 checkpoint 落盘重试 · 🔴模型健康/熔断态上 admin · 分页 · 配置化

**⬜ 规划（未动）**
T4.A 多租户/RBAC（无 tenant_id，L）· T4.C 真实计费（L）· T4.D AI 核心（记忆 Consolidate / prompt 灰度% / mcp-py 算法去桩 / 报告原生 PDF）· T3 生产硬化 ⏸（NATS 集群 / DB HA / K8s / TLS / 备份 DR，等真实流量）

---

## 14. 技术栈

| 层 | 技术 |
|---|---|
| 编排/后端 | Go · gin · **Eino(cloudwego)** · NATS/JetStream · gorm |
| LLM | OpenAI 兼容 API（DeepSeek 等）· eino-ext openai 组件 |
| 工具服务 | Go(mcp-go) · Python(mcp-py) |
| 前端 | React 19 · Vite · Tailwind · Wails(桌面端) · vitest |
| 数据 | PostgreSQL · Redis · Milvus · Neo4j · MinIO |
| 可观测 | OpenTelemetry · Jaeger · Prometheus 指标 |

---

*本文档描述当前架构的「设计」；对该设计的优缺点评价、技术债与生产化建议见 `ARCHITECTURE_REVIEW.md`。*
