## 多用户（多账号）架构评估与落地方案（草案）

本文档基于你提出的多用户需求，给出数据隔离边界、并发模型、Redis/DB 设计、以及 2核4G 服务器负载评估与分阶段落地路线。

---

## 目标与约束

### 目标（对应你的 6 点）

1. **每个用户使用自己的 API KEY**
2. **每个用户独立自动交易、独立持仓**
3. **每个用户独立配置**
4. **交易推荐全局共用**
5. **订单/交易记录独立**
6. **错误日志全局共用**

### 关键约束

- **币安限频是关键瓶颈**：公共行情接口通常按 IP 限频，单纯“多 key”无法线性扩容；必须通过共享行情缓存降低请求。
- **隔离优先级**：下单/持仓/配置/订单记录必须强隔离；推荐/行情/错误日志可以共享。

---

## 数据归属与隔离（Data Ownership）

### A. 全局共享（所有用户共用）

- **推荐（Recommendations）**：一份全局 Redis Snapshot/List
  - 建议 Key：`ats:recommendations:snapshot`
  - 后端/前端只读（不在请求中触发扫描/生成）
- **行情热数据（Market Data）**：全局缓存（Redis）
  - `ats:md:mark_price:all`（短 TTL，比如 2~5s）
  - `ats:md:ticker_24h:all`（TTL 10~30s）
  - `ats:md:klines:{symbol}:{interval}:{limit}`（TTL 30~120s）
- **错误日志（Logs）**：全局流
  - 继续使用 `ats:logs:{error|warning|info}`
  - 每条日志建议增加字段：`account_id`（便于筛选定位）

### B. 用户私有（必须隔离）

- **API KEY/SECRET（敏感）**：按账号独立存储（必须加密）
- **交易配置**：按账号独立
  - DB：`(account_id, config_key)` 唯一
  - Redis：`ats:cfg:{account_id}`（hash）
- **自动交易运行态/热数据（可选但推荐）**
  - `ats:positions:{account_id}`（更快的 UI 展示/减少后端压力）
  - `ats:orders:pending:{account_id}`（挂单/入场状态）
  - `ats:stats:{account_id}:*`（每日下单数、成交数、撤单数等）
- **交易/订单记录**：按账号独立
  - DB 表：`trades` 增加 `account_id`；统计/查询均按账号过滤

---

## 并发模型：是否需要多线程/多进程？

结论：**不推荐多线程**。更推荐以下两种模型之一：

### 方案 1（推荐先落地）：每个账号一个 `trading_system` 进程（Supervisor 管理）

- **优点**
  - 隔离强：某个账号异常/限频/崩溃不影响其他账号
  - 上线快：对现有单账号 trading_system 改动最少
  - 运维简单：Supervisor 一账号一进程
- **缺点**
  - 进程数随账号增长（内存占用会上升）
  - 若每进程都重复拉行情，会触发 IP 限频（必须配合“全局行情缓存”）

### 方案 2（后期优化）：单进程 + asyncio 多账号 worker

- **优点**
  - 资源更省，便于共享行情缓存/HTTP Session
- **缺点**
  - 隔离弱：某个账号阻塞/异常可能影响整体
  - 实现复杂：需要更严格的超时/限频/异常隔离与任务监控

---

## Redis 用法：减轻后端与交易系统压力的关键

建议将 Redis 分为四层：

1. **全局行情缓存层**（降低公共接口请求）
2. **全局推荐层**（只读 snapshot，避免“刷新=触发扫描”）
3. **账号配置层**（`ats:cfg:{account_id}`）
4. **账号运行态层**（positions/pending/stats）

额外建议：
- 使用短 TTL + 分布式锁（你已有 lock 设计），避免并发刷新造成浪涌。

---

## 数据库改造（最小必要变更）

1. 新增 `accounts` 表：
   - `id, name, api_key_enc, api_secret_enc, status, created_at ...`
   - API Key 必须加密存储（服务端用 master key 解密）
2. `trading_config` 增加 `account_id`（或新表 `trading_config_accounts`）
3. `trades` 增加 `account_id`
4. `account_snapshots` 增加 `account_id`
5. 其余按需：positions、signals（signals 可全局，positions 必须私有）

---

## 2核4G 负载评估（粗略）

负载主要来自两块：

1. **公共行情拉取/指标计算（全局）**
2. **每账号的下单/持仓同步/风控计算（私有）**

### 不做共享行情（不推荐）

- 每账号都拉 klines/mark price/ticker：会先撞到 **币安 IP 限频**，2c4g 也撑不住。

### 做共享行情 + 推荐全局（推荐）

- 公共行情只拉 1 份（Redis 分发），账号 worker 只消费缓存 + 下单/持仓同步。
- 2c4g 在“波段低频”（如 15min 扫描、每账号持仓 0~5）场景下，通常可支撑 **10~30 个账号**（视持仓监控方式与限频策略而定）。
- 若每个账号都对每个持仓开 WebSocket 监控，上限会明显降低（更建议用全局 mark price + 定时校验替代/降频）。

---

## 分阶段落地路线（推荐）

### Phase 1：最快上线（强隔离、成本最低）

- accounts + account_id 改造（DB/API/前端）
- 每账号一个 trading_system 进程（Supervisor）
- 推荐/行情继续全局缓存（Redis）
- 日志全局流（带 account_id）

### Phase 2：提升承载与稳定性

- 抽全局 MarketDataService（行情/klines 统一刷新一次）
- 每账号 worker 只做决策/下单，减少公共 API 调用
- 降低 per-position websocket 数量（用 mark price 缓存替代）

---

## 面向“更多用户”的演进战略准备（从现在就要做对的几件事）

你问“每账号一进程是不是终极方案”。我的建议是把它当作**长期默认架构**，并提前把“可演进”埋点做对，这样未来扩容不会推倒重来。

### 1）固定边界：所有“私有数据”必须天然带 account_id

- **数据库**：`trades / trading_config / account_snapshots / positions(若有)` 都必须有 `account_id`，且所有查询默认按 `account_id` 过滤。
- **Redis**：账号私有数据统一命名空间：
  - `ats:cfg:{account_id}` 或 `trading_config:{account_id}`（一账号一份配置 hash）
  - `ats:positions:{account_id}`、`ats:orders:pending:{account_id}` 等
- **API**：所有与交易/配置/统计相关的接口都要支持 `account_id`（Header 或 Path），哪怕当前只有一个账号。

这一步一旦做对，未来从“多进程”演进到“多 worker/分布式”几乎不改数据层。

### 2）把“共享层”单独做成服务：推荐/行情永远不绑定账号

- 推荐：一份全局 snapshot（你已拆成独立推荐进程/服务），后面可水平扩容但要有锁。
- 行情：建议尽早演进为全局 MarketDataService（单实例拉取 + Redis 分发），账号 worker 只消费缓存。

这一步是从 10~30 账号走向 100+ 账号的关键，否则会先撞 Binance IP 限频。

### 3）演进路线（从易到难，逐步替换，不做“重写”）

1. **阶段A（现在）**：每账号一个进程（Supervisor）  
   - 最稳、隔离最好、上线快
2. **阶段B（账号增多）**：引入“控制器 + worker”但仍可单机  
   - 控制器负责：调度、限频预算、健康检查、任务重启
   - worker 负责：每账号决策/下单/同步（可仍按进程隔离）
3. **阶段C（规模更大）**：队列化/分布式（K8s/多机）  
   - 账号按 `account_id` 分片到不同节点（sharding）
   - 共享服务（行情/推荐）做成单独部署，或按区域分片

### 4）安全策略提前统一：API Key/Secret 必须与“普通配置”分离

- 强烈建议：API Key/Secret 存 `accounts` 表，**加密存储**（服务端 master key 解密），前端永不回传 secret 明文。
- 交易进程只拿到自己账号的解密结果（进程隔离的优势）。

---

## 风险提示与建议

- **安全**：API Key 必须加密存储；前端永远不返回明文 secret。
- **限频**：公共接口一定要共享缓存；多账号并发拉行情会让整体不可用。
- **隔离**：交易执行建议多进程优先；后期再做单进程多 worker 的资源优化。

