- middleware.md: 集成契约+3不变量+执行流 (157→136行) - saas.md: 移除安全重复→引用security.md+Token Pool算法 (231→173行) - security.md: 吸收saas认证内容成为安全唯一真相源 (158→199行) - memory.md: 最大压缩363→147行+Hermes洞察提炼+4不变量 Co-Authored-By: Claude Opus 4.7 <noreply@anthropic.com>
174 lines
6.8 KiB
Markdown
174 lines
6.8 KiB
Markdown
---
|
||
title: SaaS 平台
|
||
updated: 2026-04-22
|
||
status: active
|
||
tags: [module, saas, billing, relay]
|
||
---
|
||
|
||
# SaaS 平台
|
||
|
||
> 从 [[index]] 导航。关联模块: [[routing]] [[chat]] [[security]]
|
||
|
||
## 设计决策
|
||
|
||
**核心定位: SaaS 是 Tauri 桌面端的中枢,不是独立 Web 应用。**
|
||
|
||
| 决策 | 为什么 |
|
||
|------|--------|
|
||
| Token Pool 集中管理 | 桌面端不持有 LLM API Key,SaaS 维护共享 Key 池做 RPM/TPM 轮换,支持用量追踪和计费 |
|
||
| 16 模块目录划分 | 按业务域高内聚:auth/relay/billing/knowledge/model_config/account/agent_template/industry/role/prompt/scheduled_task/telemetry/migration/models/tasks/workers |
|
||
| 137 routes + 13 路由模块 | main.rs 用 `.merge()` 统一注册,每个模块独立维护路由 |
|
||
| 7 后台 Workers | 用量记录/聚合、限流清理、token 清理、embedding 生成等异步任务解耦 |
|
||
| 认证与安全 | 详见 [[security]] |
|
||
|
||
## 关键文件 + 数据流
|
||
|
||
### SaaS 模块结构
|
||
|
||
16 个目录 (`crates/zclaw-saas/src/`):
|
||
|
||
```
|
||
account/ agent_template/ auth/ billing/ industry/
|
||
knowledge/ migration/ model_config/ models/ prompt/
|
||
relay/ role/ scheduled_task/ tasks/ telemetry/ workers/
|
||
```
|
||
|
||
### 核心文件
|
||
|
||
| 文件 | 职责 |
|
||
|------|------|
|
||
| `crates/zclaw-saas/src/main.rs` | 路由注册入口 (13 个 .merge()) |
|
||
| `crates/zclaw-saas/src/relay/handlers.rs` | 聊天中转 + Token Pool 分配 |
|
||
| `crates/zclaw-saas/src/billing/` | 配额递增/订阅/支付回调 |
|
||
| `crates/zclaw-saas/src/knowledge/` | 知识库 CRUD + pgvector (最大模块, 24 routes) |
|
||
| `crates/zclaw-saas/src/workers/` | 7 个后台 Worker |
|
||
| `crates/zclaw-saas/migrations/` | SQL 迁移 (38 文件, 42 CREATE TABLE) |
|
||
| `admin-v2/src/pages/` | 17 页管理后台 |
|
||
| `desktop/src/lib/saas-client.ts` | 前端 SaaS API 客户端 |
|
||
| `desktop/src/store/saasStore.ts` | SaaS 认证状态 |
|
||
|
||
### 数据流
|
||
|
||
```
|
||
桌面端请求 (ChatPanel)
|
||
→ Tauri invoke / HTTP SSE
|
||
→ SaaS Relay (POST /api/v1/relay/chat/completions)
|
||
→ JWT 验证 → Token Pool 选择 Key → LLM API
|
||
→ SSE 流式返回
|
||
→ 桌面端 streamStore.onDelta 渲染
|
||
```
|
||
|
||
### 集成契约
|
||
|
||
| 方向 | 接口 | 说明 |
|
||
|------|------|------|
|
||
| Called by <-- desktop | Tauri invoke / HTTP SSE | Chat relay, billing, auth |
|
||
| Calls --> relay handlers | POST /api/v1/relay/chat/completions | Token Pool RPM/TPM 轮换 |
|
||
| Provides --> admin | 137 routes | User/billing/knowledge/model 管理 |
|
||
|
||
### API 分布
|
||
|
||
| 模块 | 路由数 | 核心端点 |
|
||
|------|--------|---------|
|
||
| knowledge | 24 | 分类/条目/搜索/上传/版本/结构化 |
|
||
| model_config | 19 | Provider/模型/Key/模型组/用量 |
|
||
| billing | 12 | 订阅/用量/支付/mock/回调/invoice |
|
||
| account | 12 | CRUD/状态/token/设备/操作日志/dashboard |
|
||
| agent_template | 11 | 模板 CRUD + 创建 Agent + 分配 |
|
||
| auth | 9 | POST /auth/{register,login,refresh,logout} + TOTP + password |
|
||
| industry | 8 | 行业 CRUD + 账户分配 |
|
||
| migration | 8 | 配置项 CRUD + 分析/seed/sync/diff |
|
||
| prompt | 6 | Prompt CRUD + 版本/回滚 |
|
||
| role | 6 | 角色/权限模板 CRUD |
|
||
| telemetry | 4 | 上报/统计/日报/审计 |
|
||
| relay | 5 | POST /relay/chat/completions + GET /relay/models |
|
||
| scheduled_task | 2 | 定时任务 CRUD |
|
||
|
||
### 数据表 (42 CREATE TABLE)
|
||
|
||
核心表: users, agents, conversations, messages, billing_*, knowledge_*, model_configs, roles, permissions, scheduled_tasks, telemetry, agent_templates, saas_schema_version, user_profiles, trajectory_records, industries, account_industries
|
||
|
||
## 代码逻辑
|
||
|
||
### Token Pool RPM/TPM 轮换算法
|
||
|
||
```
|
||
SaaS Relay 收到请求
|
||
→ 验证 JWT → 提取 user_id
|
||
→ Token Pool 选择 Key:
|
||
1. priority ASC (高优先级优先)
|
||
2. last_used_at ASC (最久未用优先)
|
||
3. cooldown 检查 (跳过冷却中的 Key)
|
||
4. RPM/TPM 滑动窗口检查 (当前窗口是否超限)
|
||
→ 转发请求到 LLM API
|
||
→ record_usage worker 异步记录
|
||
```
|
||
|
||
### Workers (7 个)
|
||
|
||
| Worker | 文件 | 职责 |
|
||
|--------|------|------|
|
||
| record_usage | workers/ | 用量记录 (relay 后异步) |
|
||
| aggregate_usage | workers/ | 用量聚合 (日报/月报) |
|
||
| generate_embedding | workers/ | 内容分块 (embedding deferred, pgvector 就绪) |
|
||
| log_operation | workers/ | 操作日志 |
|
||
| cleanup_rate_limit | workers/ | 限流记录清理 |
|
||
| cleanup_refresh_tokens | workers/ | 刷新 token 清理 |
|
||
| update_last_used | workers/ | 模型最后使用时间更新 |
|
||
|
||
### 计费流程
|
||
|
||
```
|
||
用户请求 relay → quota_check_middleware 检查月度配额
|
||
→ 通过: relay 正常执行
|
||
→ record_usage worker 递增 relay_requests + input_tokens
|
||
→ aggregate_usage worker 定期聚合
|
||
→ 超额: 返回 429 QuotaExceeded
|
||
```
|
||
|
||
## 活跃问题 + 陷阱
|
||
|
||
| 问题 | 级别 | 说明 |
|
||
|------|------|------|
|
||
| Admin 用量统计显示 0/0 | P2 Open | Dashboard 17 requests / 6304 tokens,但 Usage 页 0/0,数据源不一致 |
|
||
| 桌面端 Token 统计为 0 | P2 Open | 前端 token 统计未接通后端数据源 |
|
||
| Deepseek 中转任务卡 processing | P3 Open | 特定模型 relay 任务状态不更新 |
|
||
| Embedding 生成未实现 | 长期 | pgvector 索引就绪,generate_embedding worker 逻辑空 |
|
||
| AuthGuard 竞态条件 | P1 Deferred | 并发请求时可能绕过认证 |
|
||
|
||
陷阱:
|
||
- SaaS 数据库需要 PostgreSQL (`docker-compose.yml`),不是 SQLite
|
||
- Token Pool 的 RPM/TPM 是滑动窗口不是固定窗口,测试时注意时间边界
|
||
- `saas-config.toml` 支持 `${ENV_VAR}` 环境变量插值
|
||
- knowledge 是最大模块 (24 routes),修改时影响面广
|
||
|
||
## 变更日志
|
||
|
||
| 日期 | 变更 | 提交 |
|
||
|------|------|------|
|
||
| 2026-04-21 | Embedding 接通 + 自学习 A/B 线 | — |
|
||
| 2026-04-17 | E2E 测试 129 链路,7 Bug 修复 | — |
|
||
| 2026-04-15 | Heartbeat 统一健康系统 | — |
|
||
| 2026-04-12 | 行业配置 + 管家主动性全栈 5 Phase | — |
|
||
| 2026-04-09 | Hermes Intelligence Pipeline 4 Chunk | 684 tests PASS |
|
||
|
||
### 测试覆盖
|
||
|
||
| 功能 | 测试文件 |
|
||
|------|---------|
|
||
| 认证流程 | `crates/zclaw-saas/tests/auth_test.rs` |
|
||
| 认证安全 | `crates/zclaw-saas/tests/auth_security_test.rs` |
|
||
| 账户 CRUD | `crates/zclaw-saas/tests/account_test.rs` |
|
||
| 账户安全 | `crates/zclaw-saas/tests/account_security_test.rs` |
|
||
| 计费 | `crates/zclaw-saas/tests/billing_test.rs` |
|
||
| 知识库 | `crates/zclaw-saas/tests/knowledge_test.rs` |
|
||
| 模型配置 | `crates/zclaw-saas/tests/model_config_test.rs` |
|
||
| Prompt | `crates/zclaw-saas/tests/prompt_test.rs` |
|
||
| 权限矩阵 | `crates/zclaw-saas/tests/permission_matrix_test.rs` |
|
||
| Relay | `crates/zclaw-saas/tests/relay_test.rs` |
|
||
| Relay 验证 | `crates/zclaw-saas/tests/relay_validation_test.rs` |
|
||
| 角色 | `crates/zclaw-saas/tests/role_test.rs` |
|
||
| 定时任务 | `crates/zclaw-saas/tests/scheduled_task_test.rs` |
|
||
| Telemetry | `crates/zclaw-saas/tests/telemetry_test.rs` |
|
||
| 配置同步 | `crates/zclaw-saas/tests/migration_test.rs` |
|