# 指标数据契约(宏观课程站 × Macronomy 宏观站 共享) > 生效日期:2026-10-30 > 适用范围:`/macro-course/` 数据中心指标、`content/` 书稿正文引用的宏观数字 > 数据上游:Macronomy 宏观站指标宇宙(`/api/v1/macro/indicator-universe`)与序列接口(`/api/v1/macro/chart/{id}`) ## 一、为什么有这份契约 同一指标此前有两套并行的身份:课程站叫 `gdp`、序列号 `A191RL1Q225SBEA`;宏观站叫 `FRED/A191RL1Q225SBEA`。名称、单位、频率各写一份,数值各写一份,互不对账。 本契约把两站合并到**一个指标 id**(`macro_id`),口径与数值只在上游维护一次,下游只消费。 ## 二、字段定义 | 字段 | 类型 | 必填 | 来源 | 说明 | |---|---|:--:|---|---| | `id` | string | 是 | 课程站 | 课程站内部唯一标识,页面与书稿引用用 | | `macro_id` | string | 是 | 宏观站 | 宏观站指标宇宙 id,形如 `FRED/CPIAUCSL`、`AKSHARE/CN_CPI_YOY`。全局唯一,是两站对接的锚点 | | `cn` / `en` | string | 是 | 课程站 | 中文名 / 英文名 | | `cat` | string | 是 | 课程站 | 教学分类:growth / inflation / labor / rates / fx 等 | | `unit` | string | 是 | 双方 | 单位。两站必须一致,不一致记一级问题 | | `freq` | string | 是 | 双方 | 频率:D / M / Q / A | | `country` | string | 是 | 宏观站 | 国家或 GLOBAL | | `source` | string | 是 | 宏观站 | 来源机构代码(FRED / AKSHARE / EASTMONEY / BIS …) | | `source_url` | string | 否 | 宏观站 | 来源页地址 | | `caliber` | string | 否 | 人工 | 口径说明:统计范围、是否季调、价格口径、基期、覆盖对象。**没有就留空并标 pending,不准臆造** | | `caliber_machine` | object | 是 | 宏观站 | 机器口径:`{name, unit, frequency, country, source}`,由上游 API 原样带回,供对账 | | `points` | array | 是 | 宏观站 | 时间序列点 `[{date, value}]`,按日期升序 | | `period` | string | 是 | 宏观站 | 快照窗口,如 `1y` | | `as_of` | string | 是 | 宏观站 | 上游数据截止日期 | | `status` | enum | 是 | 人工 | `verified` 已核 / `pending` 待核 / `suspect` 存疑。**只反映口径要件是否齐备**,与再分发授权无关 | | `redistribution` | enum | 是 | 上游 | `open` 官方公开数据(注明来源可用)/`restricted` 商业数据源(再分发需授权确认)/`unknown` 未标注 | | `verified_from` | string | 是 | 人工 | 口径核验依据:`catalog:research-macro/current` 或 `chart:/api/v1/macro/chart` | | `verified_at` | string | 是 | 人工 | 口径核验日期(YYYY-MM-DD) | | `derive_kind` | enum | 否 | 构建器 | `yoy12` / `diff` / `x100`,派生方式 | | `updated_at` | string | 是 | 构建器 | 快照生成时间(ISO8601) | ## 三、状态纪律(三态,不许自创) | 状态 | 含义 | 正文可否引用 | |---|---|---| | `verified` | 机器口径齐备,且人工口径已回源核对并写明(含单位、频率、覆盖区间、季调标注、数据性质) | 可引用数值,须同时标注口径与来源 | | `pending` | 机器口径齐备,但人工口径仍缺要件(如报价类型未标注) | **可引用定性表述,不可引具体数值** | | `suspect` | 上游返回缺字段、单位不一致或值异常 | 不可引用,须人工回查 | 与书稿台账的「已核 / 待核 / 存疑」一一对应。台账与本契约的状态必须一致,同一指标在两处状态不同即记为问题。 ### 口径与再分发是两件事 `status` 回答「这个数是什么口径、能不能引用」;`redistribution` 回答「能不能把它搬到另一个站点展示」。 - `open`:来源为官方公开统计(`dataNature=official`),注明来源与提取日期即可使用; - `restricted`:来源为商业数据源(`dataNature=commercial`,如 ISM 指数、持牌行情源),口径可以核、页面可以引用其最新值,但**整段序列落盘再分发需授权确认**。这类指标在页面上标注「商业数据源」。 当前 22 项中:17 项 `open`(FRED 与美国官方统计),5 项 `restricted`(ISM 制造业 PMI 1 项 + 商业汇率源 4 项)。 ## 四、红线校验(构建期执行,不通过即中止) 1. `id` 唯一、`macro_id` 唯一; 2. `unit` 非空; 3. `status` ∈ {verified, pending, suspect}; 4. `points` 的 `date` 必须可解析、严格升序、无重复;`value` 为数值或 null,不得为字符串; 5. `as_of` 必须存在且可解析; 6. 课程站 `unit` 与上游 `caliber_machine.unit` 不一致 → 一级问题(派生且换算已声明的降为三级提示); 6b. `status=verified` 但 `caliber` 为空 → 中止构建; 6c. `redistribution` 不在 {open, restricted, unknown} → 中止构建; 7. 课程站教学参考值与快照最新值相对偏差 > 20% → 二级问题(教学值可能过时); 8. 上游取数失败 → 沿用上一份快照并记告警;**连续两次失败中止构建**,不允许用空快照覆盖已有数据。 ## 四之二、口径回源路径 口径不靠记忆写。两条可核来源: 1. **宏观站指标目录** `/var/www/chronoscope/research-macro/current/catalog.json`(173,893 条),字段含官方名称、单位、频率、覆盖区间、点数、数据性质(`dataNature`)、是否官方(`isOfficial`)。本轮 22 项中的 19 项取自此目录。 2. **序列接口元数据** `/api/v1/macro/chart/{macro_id}` 的 `indicator` 对象与数据行 `frequency` 字段(目录未收录时使用,本轮 3 项)。 已抽取的 22 项元数据存档在 `shared/indicator-metadata.json`,可复核。 **注意**:宏观站与本机均无法直连 FRED 官网,官方 Notes(口径文字说明)拿不到,因此「是否季调」只采信上游名称中的显式标注;名称未标注者写明「上游未标注季调属性」,不臆断。 ## 五、更新节奏 - 快照由 `build/fetch_metrics.py` 在构建期抓取,页面运行时**不发任何 API 请求**; - 日频指标每日构建刷新一次;周频/月频随构建刷新; - 快照文件:`assets/data/metrics.json`(页面只读这个文件)。 ## 六、两站职责边界 | | 宏观站 | 课程站 | |---|---|---| | 指标宇宙与序列 | 唯一真源 | 不复制序列,只引用 `macro_id` | | 口径 | 维护 `caliber_machine` | 维护教学用 `caliber`(可为空,标 pending) | | 数值 | 维护 | 只做快照消费与教学呈现 | | 教学解释 | 不负责 | `teaching` / `watch` / `desc` 由课程站维护 |