Files
sanguo_vnpy_v2/docs/archive/design/provider-mcp-expose-design.md
T
claude_dev 4ebbd434a6 docs(archive): 过期文档归档波——14 件墓碑+台账补全+两轮审计报告入库 [nas]
- 归档 12 件(git mv 保历史,audit/20261001_docs_audit/ §2.1 判定):
  deployment/{vps-native-brain,windows-bridge-setup,d-phase-windows-deploy,README}
  (miniQMT/FastAPI-bridge 退役架构,09-08)+vps-deploy-pending(一次性任务使命
  终结)+specs/phase3b-vue(里程碑已兑现)+plans/{phase3c-paper-trading,
  backtest-result-page,strategy-management-backend,factor-batch1}(已完成/被
  实态推翻)+design/provider-mcp-expose(未实施行号全失效)+research/README
  (死模板)
- 原位墓碑 2 件: sanguo_qmt_bridge/README(包内保留,运维语义退役)+
  CHANGELOG(冻结,变更历史以 git log 为准)
- 台账: audit/README 补 5 波次表+状态列+固定安全清单约定(每波必查凭据/
  鉴权面/CI 门禁 diff——历轮审计系统性盲区,docs_audit §5.2);docs/README
  索引对齐归档后实态(+design/audit 行)
- 审计报告入库: 20260927_commit_docs_consistency+20261001_architecture_
  code_audit+20261001_docs_audit 三目录

Co-Authored-By: Claude Code <notify@anthropic.com>
2026-10-01 09:08:29 +08:00

156 lines
7.5 KiB
Markdown
Raw Blame History

This file contains ambiguous Unicode characters
This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.
> **⚠️ 已归档(2026-10-01,audit/20261001_docs_audit/ §2.1 归档波)**
>
> - 归档原因:设计从未实施(全仓无 sanguo_mcp 实现)+「14 个公开方法」与全部行号引用已失效(现役 20+ 方法);重启此设计须按现码重写。
> - 现行权威:无(如需 MCP 暴露 provider 须新起设计)。
> - 处置:已移入 docs/archive/;原文全文见 git 历史(归档 commit 前一版)。
# 设计笔记:用 MCP 直接暴露 LocalUnifiedProvider 给 Claude Code
> 设计日期 2026-07-30。配套 `provider-tet-design.md` + `docs/research/openbb-platform-research.md`。
>
> 一句话定位:**给 AI 装一只「直接读本项目本地数据」的手**——把 `LocalUnifiedProvider` 的取数方法注册成 Claude Code 可调的 MCP 工具,从「请你跑数据贴给我」变成「我自己拉数据、算指标、给结论」。
---
## 一、为什么是「直接暴露」而非照搬 OpenBB
```
OpenBB 的链路(它需要 REST + Workspace,MCP 是副产品):
provider方法 → @router.command → FastAPI端点 → fastmcp 从 OpenAPI 派生 → MCP工具
本项目(不需要 REST/Workspace,跳过中间层):
provider方法 → 直接 @tool 注册成 MCP工具
```
OpenBB 建了 FastAPI 是为了给 Workspace 前端和第三方 REST 用,MCP 顺手派生。**本项目策略层直调 provider、不给第三方 REST**,纯为 MCP 去建一整套 FastAPI + Router 命令树是过度工程(YAGNI)。所以直接拿 MCP server 框架(fastmcp / `mcp` python sdk),把 provider 方法 `@tool` 注册即可。
---
## 二、解决的本项目痛点(三个实证)
| 痛点 | 现状 | MCP 暴露后 |
|------|------|-----------|
| **人肉割裂** | 你跑脚本 → 贴数据 → 我分析;或我用 `!` 让你跑命令,每查一次打断一次 | 我直接调工具拿数据,你当中转的环节消失 |
| **手搓查询错**(`feedback-verify-via-provider-exact-query`) | 我手搓 SQL `symbol='000534'` 查 dbbardata(双列)误报「19 股无日线」,实际 provider 数据完整 | 我调用的就是 provider 确切方法,**口径天然一致**,不可能手搓错 |
| **AI 不能主动取数** | 你问「000001 走势如何」,我没法直接拉数据,得绕几道 | 我直接 `get_price_panel("000001")` → 算指标 → 给结论,一句话进一个分析出 |
---
## 三、暴露哪些方法(基于真实公开方法清单)
源:`sanguo_portfolio/providers/local_unified_provider.py` 的 `LocalUnifiedProvider` 14 个公开方法。按暴露优先级分组:
### P0 — 高频取数(优先暴露,策略/回测核心)
| 方法 | 行号 | 用途 | 备注 |
|------|------|------|------|
| `get_price` | 170 | 行情(日线/15min,支持复权) | 最高频 |
| `get_closes_panel` | 272 | 多股票收盘价面板 | 回测核心,已优化 fq+UNION ALL |
| `get_constituent` | 512 | 指数成份股(治偏差版) | 选股池 |
| `get_fundamentals_df` | 582 | 基本面(已修前视偏差) | 基本面过滤 |
### P1 — 估值/风控
| 方法 | 行号 | 用途 |
|------|------|------|
| `get_value_metrics_batch` | 639 | 估值(pe/pb)批量 |
| `get_limit_status_batch` | 868 | 涨跌停状态(已优化 UNION ALL) |
### P2 — 元信息/日历
| 方法 | 行号 | 用途 |
|------|------|------|
| `get_security_info` / `get_security_info_batch` | 746 / 777 | 证券元信息 |
| `get_all_securities` | 998 | 全部证券列表 |
| `get_trade_days` | 723 | 交易日历 |
| `get_split_dividend` | 967 | 除权除息 |
### 暂不暴露(与 Vibe-Research 重叠或低频)
| 方法 | 原因 |
|------|------|
| `get_current_tick`(947) | 实时 tick,Vibe-Research 的 `query_quote` 已覆盖在线实时 |
| `get_index_stocks`(479) | 与 `get_constituent` 重叠,后者是治偏差权威版,暴露后者即可 |
---
## 四、怎么注册(薄 MCP server)
核心:server 只做「注册 + 序列化」,不写业务逻辑(业务全在 provider)。
```python
# 伪代码:sanguo_mcp/server.py
from mcp.server.fastmcp import FastMCP
from sanguo_portfolio.providers.local_unified_provider import LocalUnifiedProvider
mcp = FastMCP("sanguo")
provider = LocalUnifiedProvider(...) # 读本地 dbbardata/parquet
@mcp.tool()
def sanguo_get_price(symbol: str, start: str, end: str, interval: str = "1d") -> list[dict]:
"""获取 A 股行情(日线/15min,前复权)。symbol 如 '000001.SZ'。"""
df = provider.get_price(symbol, start, end, interval=interval)
return df.to_dict(orient="records") # JSON records,LLM 友好
@mcp.tool()
def sanguo_get_closes_panel(symbols: list[str], start: str, end: str) -> dict:
"""多股票收盘价面板(回测用)。"""
return provider.get_closes_panel(symbols, start, end).to_dict()
# ... 其余方法同理
```
### 关键约定
- **工具命名前缀 `sanguo_`**:和已挂载的 `vibe-research__*` 区分,一看就知道是本地数据
- **参数 = provider 标准字段**(symbol/start/end/interval),和 TET 笔记的 standard/extra 拆分一致
- **返回 JSON records**:参考 OpenBB `OBBject.to_llm()`(JSON records 格式),LLM 友好;大表注意别一次返回几万行(加 limit 或采样)
- **数据本地读**:工具内部仍走 `provider-local-data-only` 铁律,读 dbbardata/parquet,不打网络
---
## 五、和 Vibe-Research 的分工(互补,不重叠)
| | 数据来源 | 能查什么 | 工具前缀 |
|---|---|---|---|
| **Vibe-Research(已有 5 工具)** | 在线实时 | 当前价、新闻、研报、估值、全球股 | `vibe-research__` / `mcp__vibe-research__` |
| **本项目 MCP(本设计)** | 本地 dbbardata/parquet | 历史日线/15min、成份股、基本面历史、涨跌停、回测取数 | `sanguo_` |
互补关系:**实时用 Vibe-Research,历史/回测用 sanguo**。例如「000001 现在多少钱」用 `query_quote`,「000001 过去 5 年回测数据」用 `sanguo_get_price`。
---
## 六、和 TET 的配套(顺序很重要)
| 阶段 | 做什么 | 为什么 |
|------|--------|--------|
| 先 | **TET 化 provider**(见 `provider-tet-design.md`) | transform_data pydantic 校验,治兜底会乱,保证取数质量 |
| 后 | **MCP 暴露** | 让 AI 消费的是校验过的干净标准数据 |
**顺序不能反**:如果 provider 兜底还在(补 NaN 当停牌),MCP 暴露出去的也是脏数据,AI 拿着错数据做分析,结论全错。**先治兜底,再暴露**。
---
## 七、设计原则
1. **跳过 FastAPI/Router**(YAGNI):本项目不给第三方 REST,纯为 MCP 建它们是过度工程
2. **暴露 provider 确切方法**:根治「手搓查询口径错」,我调用的就是策略层用的同一套 API
3. **薄 server**:只注册 + 序列化,业务逻辑零下沉(全留 provider),server 永远是薄薄的胶水层
4. **本地只读**:工具内部读 dbbardata/parquet,遵守 `provider-local-data-only` 铁律
5. **大表克制**:MCP 工具面向「对话式查询」,默认带 limit/采样,几万行回测数据不该一次性灌给 LLM
---
## 八、落地步骤
1. 选 MCP 框架(`mcp` python sdk 或 fastmcp),起 `sanguo_mcp` server
2. 优先暴露 4 个 P0 方法(get_price / get_closes_panel / get_constituent / get_fundamentals_df)
3. 参数用标准字段,返回 JSON records,大表加 limit
4. 挂到 Claude Code MCP 配置(参考 Vibe-Research 的挂载方式)
5. 验证:对话里调 `sanguo_get_price("000001.SZ", ...)`,确认数据与直接调 provider 一致
6. 再逐步暴露 P1/P2
---
## 相关
- 配套设计:`provider-tet-design.md`(先治兜底,再暴露)
- 调研:`docs/research/openbb-platform-research.md`
- Vibe-Research 接入先例:`a-stock-data-integration`
- provider 本地只读铁律:`provider-local-data-only`
- 手搓查询错教训:`feedback-verify-via-provider-exact-query`