基本面数据源

📎 引用文件

本文引用的文件 - tushare_fundamentals.py - sec_edgar_client.py - sec_frames.py - _fundamental_schema.py - fundamentals_loader.py - tushare.py - base.py - financial_rigor_tool.py

目录

  1. 简介
  2. 项目结构
  3. 核心组件
  4. 架构总览
  5. 详细组件分析
  6. 依赖关系分析
  7. 性能考虑
  8. 故障排查指南
  9. 结论
  10. 附录

简介

本文件面向 Vibe-Trading 的“基本面数据源集成”,聚焦以下目标: - 财务报表数据、公司信息、SEC 文件的获取与处理机制 - Tushare 基本面数据接入、SEC EDGAR XBRL 解析与统一的基本面数据模型 - 财务指标计算、数据标准化与质量验证流程 - 财报季数据处理、异常值检测与缺失值填充策略 - 常见应用场景与最佳实践

项目结构

本项目在 backtest/loaders 下提供多源数据加载能力,其中与基本面相关的关键模块包括: - SEC EDGAR 客户端与周期帧选择:sec_edgar_client.py、sec_frames.py - 统一字段与派生指标定义:_fundamental_schema.py - SEC 基本面面板构建:fundamentals_loader.py - Tushare 基础行情与可选日度基本字段:tushare.py - Tushare 专用 PIT 安全基本面表查询:tushare_fundamentals.py - 通用校验、重试与缓存:base.py - 精确算术与一致性校验工具:financial_rigor_tool.py

graph TB subgraph "数据源" T["Tushare API"] S["SEC EDGAR (XBRL)"] end subgraph "加载层" TF["TushareFundamentalProvider<br/>PIT 切片与去重"] TL["Tushare DataLoader<br/>日频+可选 daily_basic 字段"] FL["SEC Fundamentals Loader<br/>稀疏事实->稠密面板"] SF["SEC Frames<br/>季度/年度/YTD 识别"] SC["统一字段 Schema<br/>RAW/DERIVED/SEC_CONCEPT_MAP"] end subgraph "输出" P["价格框架增强<br/>enrich_price_frames_with_fundamentals"] D["因子/研究面板<br/>load_fundamental_panel"] end T --> TL S --> FL S --> SF SC --> FL SC --> TF FL --> D TF --> P TL --> P

图表来源 - tushare_fundamentals.py:110-179 - sec_edgar_client.py:166-227 - sec_frames.py:42-129 - _fundamental_schema.py:28-193 - fundamentals_loader.py:47-131 - tushare.py:139-202

章节来源 - tushare_fundamentals.py:110-179 - sec_edgar_client.py:166-227 - sec_frames.py:42-129 - _fundamental_schema.py:28-193 - fundamentals_loader.py:47-131 - tushare.py:139-202

核心组件

章节来源 - tushare_fundamentals.py:110-179 - sec_edgar_client.py:166-227 - sec_frames.py:42-129 - _fundamental_schema.py:28-193 - fundamentals_loader.py:196-277 - tushare.py:139-202 - base.py:31-119 - financial_rigor_tool.py:143-200

架构总览

下图展示从原始数据到统一面板与价格增强的端到端流程,强调 PIT 安全与跨源统一。

sequenceDiagram participant U as "调用方" participant TFP as "TushareFundamentalProvider" participant SEC as "SEC EDGAR Client" participant SCH as "统一字段Schema" participant FLD as "SEC Fundamentals Loader" participant PR as "价格框架增强" U->>TFP : query_fundamentals(table, codes, as_of, periods, fields) TFP->>TFP : _query_pit_cut() 按 as_of 过滤 TFP->>TFP : 按 pit_date 去重(保留最新) TFP-->>U : 结构化 DataFrame U->>FLD : load_fundamental_panel(symbols, fields, freq, pit) FLD->>SEC : get_company_facts(cik) FLD->>SCH : SEC_CONCEPT_MAP/DERIVED_FIELDS FLD->>FLD : 提取稀疏事实->TTM/季度/年度 FLD->>FLD : ffill_pit 前向填充至交易日索引 FLD-->>U : {field : DataFrame(index=dates, columns=symbols)} U->>PR : enrich_price_frames_with_fundamentals(data_map, provider, fields_by_table, as_of) PR->>TFP : _query_pit_cut() 获取可见快照 PR->>PR : merge_asof 按交易日期回填 PR-->>U : 已增强的价格面板

图表来源 - tushare_fundamentals.py:136-179 - tushare_fundamentals.py:264-379 - sec_edgar_client.py:166-227 - fundamentals_loader.py:47-131 - fundamentals_loader.py:196-277

详细组件分析

Tushare 基本面数据(PIT 安全)

flowchart TD Start(["开始"]) --> Q["查询 Tushare 表"] Q --> PIT["确定 PIT 列(f_ann_date/ann_date)"] PIT --> Filter{"as_of 过滤"} Filter --> |是| Dedup["按(ts_code,end_date)去重<br/>保留最新PIT"] Filter --> |否| Dedup Dedup --> Fields["裁剪输出列(identity+fields)"] Fields --> End(["返回DataFrame"])

图表来源 - tushare_fundamentals.py:136-179 - tushare_fundamentals.py:181-230

章节来源 - tushare_fundamentals.py:110-179 - tushare_fundamentals.py:264-379

SEC EDGAR 公司信息与文件

sequenceDiagram participant C as "调用方" participant E as "SEC EDGAR Client" C->>E : cik_for(ticker) E->>E : 读取/构建 ticker->CIK 缓存 E-->>C : 返回 padded CIK C->>E : get_company_facts(cik) E-->>C : 返回 XBRL facts JSON

图表来源 - sec_edgar_client.py:118-163 - sec_edgar_client.py:166-227

章节来源 - sec_edgar_client.py:1-235

SEC 财报季识别与周期帧

flowchart TD R["一行事实(row)"] --> SP["span_days(start,end)"] SP --> CL["classify_span(days)"] CL --> K{"instant/quarter/annual/ytd?"} K --> |instant| I["instant 直接匹配任意 cadence"] K --> |quarter| Q["仅匹配 quarter"] K --> |annual| A["仅匹配 annual"] K --> |ytd| Y["不匹配任何 cadence"]

图表来源 - sec_frames.py:42-129

章节来源 - sec_frames.py:1-129

统一基本面数据模型(RAW/DERIVED/SEC_CONCEPT_MAP)

classDiagram class 统一字段Schema { +RAW_FIELDS +DERIVED_FIELDS +SEC_CONCEPT_MAP +resolve_field(field) +list_supported_fields() } class 派生指标 { +roe +roa +gross_profitability +asset_growth +accruals +leverage } 统一字段Schema --> 派生指标 : "compute/dependencies"

图表来源 - _fundamental_schema.py:28-193

章节来源 - _fundamental_schema.py:1-227

SEC 基本面面板构建(TTM/季度/年度)

flowchart TD S["公司facts(JSON)"] --> X["_extract_concept_series()<br/>union概念/去重/窗口筛选"] X --> T{"freq==ttm?"} T --> |是| R["4期滚动求和<br/>维护filed锚点"] T --> |否| N["保持原频率"] R --> F["ffill_pit 前向填充"] N --> F F --> P["输出{field: DataFrame}"]

图表来源 - fundamentals_loader.py:47-131 - fundamentals_loader.py:169-193 - fundamentals_loader.py:196-277

章节来源 - fundamentals_loader.py:1-501

Tushare 日频与可选基本字段

章节来源 - tushare.py:1-383

数据质量与校验

章节来源 - base.py:31-119 - financial_rigor_tool.py:143-200 - financial_rigor_tool.py:442-572

依赖关系分析

graph LR TFP["TushareFundamentalProvider"] --> SCH["_fundamental_schema"] FL["SEC Fundamentals Loader"] --> SEC["sec_edgar_client"] FL --> SF["sec_frames"] FL --> SCH TL["Tushare DataLoader"] --> BASE["base 工具"] TFP --> BASE FL --> BASE

图表来源 - tushare_fundamentals.py:110-179 - fundamentals_loader.py:196-277 - sec_edgar_client.py:166-227 - sec_frames.py:42-129 - base.py:243-439

章节来源 - tushare_fundamentals.py:110-179 - fundamentals_loader.py:196-277 - sec_edgar_client.py:166-227 - sec_frames.py:42-129 - base.py:243-439

性能考虑

[本节为通用性能建议,无需特定文件引用]

故障排查指南

章节来源 - tushare.py:18-80 - sec_edgar_client.py:166-227 - fundamentals_loader.py:386-416 - base.py:31-119 - financial_rigor_tool.py:143-200

结论

[本节为总结性内容,无需特定文件引用]

附录

[本节为补充说明,无需特定文件引用]