经济日历
cMind 提供自己的经济日历 — 发布日程、实际值、预测、修订和数据驱动的影响模型 — 源自一级权威(央行和国家统计机构),零依赖于 ForexFactory、FXStreet、Investing.com 或任何聚合器。它是某时间点正确的,保持 ≥10 年的历史,并连接到交易、公共 API、MCP、cBot、AI、警报和回测。它是一个解耦的模块:可以禁用它对交易核心零影响。
状态。 P0–P4 已实现并发布。域核心、持久化(EF
calendar模式、仅追加读/写、FRED + BLS + 央行日程来源、带每源新鲜度跟踪的配置门控摄取工作者)、版本化 JWT REST API、移动优先/economic-calendarUI、MCP 工具、cBot JWT API、高影响事件警报、跟单交易新闻封锁暂停、 回测事件叠加层、SSE 流、HMAC 签名 webhooks 以及类型化的CmindCalendarClient均已实现并通过集成测试。P5 附加功能(意外分析、iCal/CSV 导出、关键词搜索、 可插拔共识)是剩余项目 — 请参阅下方的推出阶段。
与众不同之处
针对领先日历的常见抱怨成了我们的设计约束:
- 无自动影响评级变更。我们的影响评级是确定性、版本化和可审计的。每次变更都是带时间戳的记录修订 — 从不自动覆盖。用户可以精确看到为什么一个事件是高影响。
- **每个事件一个 UTC 锚。**每个事件锚定到一级源官方日程表中的单个 UTC 瞬间;源自身的时区被存储,按用户渲染使用显式 IANA 时区且 DST 由区域数据库处理 — 从不手动 ±1h 切换。
- **完整修订链,到处都是。**原始值和每次修订都是一级公民,通过 API、MCP 和 cBot 表面相同地公开。
- **≥10 年历史,无墙。**无限制的浏览范围;无 60 天上限,无注册门。
- **构建时的时间点。**每个事实携带
KnownAt(我们何时得知)和EffectiveAt(事件瞬间)。"日历在时间 T 看起来的样子"是一级查询,所以回测新闻规则的行为与实时完全一样 — 在历史中使用修订值无前向查看。
影响模型
影响分数是纯确定性函数在 [0, 100],分段为低 / 中 / 高 /
关键。其输入仅是评分时已知的数据(无未来泄露):
- 序列先验 — 指标类的基线权重(利率决议重于 CPI,重于小型调查)。
- 已实现波动性足迹 — 该序列过去发布后窗口中主要受影响符号的中位绝对返回:"这次发布历史上移动价格这么多。"
- 意外敏感性 — 绝对意外(z 分数)与发布后移动的历史相关性有多强。
分数用固定权重混合这些并标记 ImpactModelVersion。重新计算是显式、记录的操作,产生新修订 — 从不改变 — 所以分数总是从其输入可复现。
国家 → 货币 → 符号映射
最常被引用的算法集成纸切被一次性解决,作为纯函数:国家映射到其货币(每个欧元区成员转向 EUR),货币映射到在任一腿上引用它的监视列表符号。所以 EURUSD 受到 EU 和 US 事件影响;XAUUSD 是 USD 敞口;US500 映射到 USD。这驱动新闻过滤、受影响符号解析和停机数学。
新闻窗口政策
NewsWindowRule 是 { minImpact, beforeMinutes, afterMinutes, currencies?, series? }。单个、共享、纯实现回答"瞬间 T 是否在符号 S 的停机内?" — 用于 cBot 新闻过滤、复制交易暂停和 AI 风险卫士,所以它们永不分歧。在不确定时停机答案默认到配置的保守值(默认失败关闭),所以数据缺口永不静默绿光交易通过高影响发布。
时间点与修订
实际、预测和影响分数是仅追加。每个事件拥有已排序修订链,单调在 KnownAt:
Scheduled— 事件首次被排定(先前影响,无实际)。Released— 第一个印出的实际值到达。Revised— 后来修订值到达。Rescheduled— 源移动了发布瞬间(可审计、可警报)。Rescored— 影响分数在新模型版本下被重计算。
查询 as of 一个过去瞬间返回恰好那时已知的修订 — 保证杀死回测新闻规则中的前向查看。
预测 / 共识
经济学家的调查中位数不被一级源自由发布 — 它是聚合器的专有增值,我们不虚造它。事件模式携带可空 Forecast;部署可能通过可选 IForecastProvider 端口连接许可共识源(自带键,默认关闭)。先前值和修订总是来自官方源。
数据源
两个解耦层,全部一级 — 从不一个聚合器:
- 日程 / 时机: FRED 发布日历;国家统计机构(BLS、BEA、Census、 Eurostat、ONS、Destatis、INSEE、e-Stat、ABS、StatCan);央行会议日历(Fed、ECB、 BoE、BoJ、RBA、BoC、SNB、RBNZ)。
- 实际值: FRED(带版本日期用于修订和时间点)、加 BLS、BEA、Census、 ECB SDW、Eurostat 和 OECD SDMX API。
一个死源降级仅那个源的覆盖;日历持续服务其他一切 并将缺口表面为新鲜度指标。
速率限制与备份计划
外部提供商发布速率限制(FRED 允许 ~120 请求/分钟)。日历构建所以它 从不触发提供商的限制,且被节流或断开从不降级读:
- **主动节流。**每个源的 HTTP 客户端通过共享、线程安全的速率门,间隔出站请求到配置预算(
App:Calendar:FredRequestsPerMinute,默认 100 — 故意在提供商上限下)。请求排队并分步,从不突发。 - **遵重
429 Retry-After。**如果提供商曾返回429 Too Many Requests,门将整个源退后服务器请求的冷却(或App:Calendar:RateLimitBackoff,默认 60s)在下一次调用前 — 无紧密重试循环。 - **标准韧性。**每个源客户端也继承应用广范韧性处理器(带抖动重试 + 熔断器、超时),所以瞬间故障被吸收,持续故障源被停泊(其覆盖变陈旧)无影响其他。
- 备份计划 — 持久读穿缓存。读从不通过调用提供商服务。一旦范围被取得它被持久仅追加到 Postgres 并永久从那里服务(见§"按需加载")。所以即使源被速率限制或宕机,日历持续从缓存、时间点正确的数据回答;缺失跨度简单保持未覆盖,并在下一摄取周期重试。停机答案额外在不确定时失败到保守默认,所以数据缺口永不绿光交易通过发布。
- **便宜轮询。**条件提取(ETag / If-Modified-Since / 源版本游标)和"一次取一个跨度,永不再来"缓存保持实际请求量远在任何限制下在正常操作中 — 速率门是安全网,不是通用路径。
启用 / 禁用
两个独立层,恰好像其他 cMind 功能:
- 层 1 — 运行时功能切换 (
Feature.EconomicCalendar)从功能管理员 UI 翻转; 无重部署,即时生效。 - 层 2 — 白标签硬门 (
App:Branding:EnableEconomicCalendar,默认true)。一个 经销商设置它false来完全移除功能;操作员随后无法重新启用它。
有效状态是 Branding.EnableEconomicCalendar && FeatureToggle.EconomicCalendar。禁用时,
nav 条目隐藏,/economic-calendar、/api/calendar/** 和 MCP 日历工具返回
清洁功能禁用 404 — 从不 500。持久化历史在运行时切换关闭时被保持
所以重新启用是即时的。
推出阶段
- P0 — 域核心 (已实现):聚合根、值对象、端口、影响模型、 国家→符号映射、新闻窗口政策、两层门、完整单元组件。
- P1 — 持久化 + 一个源 (已实现):EF
calendar模式(自己的表、仅追加、 热索引)、读穿IEconomicCalendar读者带时间点asOf、幂等 仅追加写服务、FRED 连接器后面有韧性类型客户端、配置门控 摄取工作者;Testcontainers 集成测试(持久化、PIT、幂等性、停机)。 - P2 — 公共 JWT REST API + Web UI (已实现):版本化、JWT 保护的
/api/calendar/v1API — 客户端发行、令牌交换和核心读端点(事件、历史、序列、 意外、下一、停机、受影响符号、健康)带范围执行和两层门、 集成测试。加上移动优先**/economic-calendar页面** — 门控、完整本地化 (23 种语言)即将发布的发布议程作为手机友好卡带颜色带状影响芯片 和 MudBlazor过滤对话框(货币 + 最小影响 + 从日期选择器跳转到 任何过去日期跨完整历史 — 无 60 天上限,无墙);nav 条目、烟雾/移动/a11y/E2E 测试。一个按指标序列历史页面(/economic-calendar/series/{code},从每个 事件链接)列出序列的完整打印历史。意外图表 + 无限滚动浏览器跟随。 - P3 — 更多源 & 预热 (开始):核心序列目录(CPI、Core CPI、NFP、
失业、GDP、PCE、美联储基金、零售销售 → 它们的 FRED id)在启动时自动播种,
一次性、幂等、年分块主动回填拉它们的 ≥10 年历史所以通用情况
温暖无等待用户未命中。摄取默认启用
(
App:Calendar:IngestionEnabled,默认true):中央银行日程源需要无 API 键,所以 FOMC / ECB / BoE 决议日历开箱填充 — 回填在启动时播种那些 会议日期穿越既然最近历史又向前视野,所以浏览上个月(或任何 过去窗口)显示会议甚至在任何 FRED/BLS 键被配置前;值序列一旦 它们的键被设置就填入。工作者遵重日历的两层门 — 白标签部署或 所有者禁用经济日历功能停止摄取,且App:Calendar:IngestionEnabled=false显式关闭它。按源新鲜度现在是真实的:工作者记录每个源的最后 成功轮询、连续故障计数和一个触发熔断器标志(在应用设置中持久化, 跨进程),且/health端点 +calendar_healthMCP 工具报告真实stale判决按源。BLS(第 2 值源)和央行日程源(FOMC / ECB / BoE 决议日期,回填穿越历史和向前同步到工作者的视野窗口) 在里面。仍待:BEA/Census/ECB-SDW/Eurostat/OECD 值源和协调通道。 - P4 — 深集成:MCP 工具 (已实现 — 完整读 API 奇偶性:
calendar_events、calendar_event、calendar_history、calendar_series、calendar_surprises、calendar_next、calendar_blackout、calendar_affected_symbols、calendar_health,门控在功能上) 和 警报EconomicEvent触发 (已实现 — 一个AlertRule在即将发布前 N 分钟在/以上 选择的影响处触发,可选地缩小到货币;由既存警报工作者无 AI 计算, 按发布去重;通过POST /api/alerts/rules/economic-event创建)。prop-guard 新闻停机门 和复制交易停机暂停在里面(§5.1 — 选择性App:Copy:NewsPauseEnabled,默认关闭:一个源 开放其符号坐在关键影响停机内被跳过,热路径字节相同关闭时)。回测事件叠加在里面 —GET /api/calendar/v1/for-symbol和calendar_events_for_symbolMCP 工具返回时间点正确事件影响符号在 窗口,且实例/回测报告页面在股权曲线下呈现落在回测 窗口内的高影响发布(所以作者看到哪些交易落在 NFP),门控和 本地化。整个计划现在已实现。 - P5 — 额外:意外分析、iCal/CSV 导出、关键字搜索、可插入共识。
有关集成表面,请参阅cBot & REST API 参考。