Expand description
Broker → supported currencies 表 + currency 校验 helper
v1.4.105 (eli funds-currency-display-suggestion 2026-04-29 P0):
触发: eli 实测 acc=70524409 (Moomoo CA) /api/funds:
- 请求
currency=USD/HKD/SGD都返同一份 CAD 口径 - HKD/SGD 不该支持却 silent 不报错
C++ 对齐: APIServer_Trd_GetFunds.cpp:496-511 CheckCurrencyValid 调
INNData_Trd_CommonCurrency::GetAccountValidCurrency(accItem) 拿 broker
supported currency set, 不在内 → 返 NNData_StaticText_InvalidCurrency
“This account does not support converting to this currency”.
C++ 静态表: INNData_Trd_CommonCurrency.cpp:4-14 8 个静态 set:
HK Future (Futu HK) HKD/USD/CNH/JPY
SG Future (FutuSG) HKD/USD/CNH/JPY/SGD
MY Future (FutuMY) MYR/CNH/JPY/SGD/HKD
HK Universal (Futu HK) HKD/USD/CNH/JPY
US Universal (FutuInc) HKD/USD/CNH/JPY/SGD
SG Universal (FutuSG) HKD/USD/CNH/JPY/SGD
AU Universal (FutuAU) HKD/USD/CNH/JPY/SGD/AUD
CA Universal (FutuCA) USD/CAD ← eli 测试账户
MY Universal (FutuMY) MYR/CNH/USD/SGD/HKD
JP Universal (FutuJP) JPY/USD单币种账户 (其他 trd_market): 由 TrdMarket → currency 派生 (HK→HKD / US→USD / CN/HKCC→CNH).
历史教训 (用户 2026-04-29 强调):
“上一次修复就是因为 deger 提到了 SGD, 结果就把返回 SGD 当作了正确结果.”
即: 不能只 trust backend 返的 currency. 必须 broker → supported 表先验, Moomoo CA 账户 (security_firm=5) 不支持 SGD, 即使 backend 真返了 SGD 也 是 stale cache / 错误 routing. 本 helper 在 daemon-side 做 pre-check, 不 发 backend, 直接返结构化 error (Layer A 防御).
相关: pitfall #36 (SDK metadata 不可信, code/broker 才是真相), pitfall #45 (silent-success — fallback 返 CAD 而无 loud reject), pitfall #51 (对齐 C++ 减法 — 抄 C++ 表, 不发明).
Modules§
- currency_
id - Trd_Common.proto::Currency enum (对齐 C++ + Rust proto): 0=Unknown, 1=HKD, 2=USD, 3=CNH, 4=JPY, 5=SGD, 6=AUD, 7=CAD, 8=MYR. USDT (9) 不在 C++ 静态表里, 是 daemon-only 扩展 (USDT 不是 broker universal account 支持的法币, 不能 view 转换), 故不进 broker_currencies 任何 set.
- legacy_
backend_ fund_ market_ id - Backend raw
Account.marketfund 子市场值 (v1.4.106 Finding D). - security_
firm_ id - Trd_Common.proto::SecurityFirm enum (对齐 C++): 1=FutuSecurities (Futu HK), 2=FutuInc (Moomoo US), 3=FutuSG, 4=FutuAU, 5=FutuCA (Moomoo CA), 6=FutuMY, 7=FutuJP.
- trd_
market_ id Trd_Common.proto::TrdMarketenum (对齐 OpenD canonical NN_TrdMarket values, 不是 AppFTTradeEnableMarket也不是 backend rawAccount.market).
Enums§
- Account
Kind - 账户类型分类 (用于查 supported currencies 表)
- Currency
Validation - Layer A 校验结果 (用 enum 让 caller 区分四种状态)
Functions§
- broker_
label - security_firm enum int → 对齐 broker 标签 (用于 error message)
- classify_
account - 账户类型识别 — 对齐 C++
INNData_Trd_CommonCurrency::GetAccountValidCurrency(cpp:92-126) 的 3 分支结构: - classify_
account_ with_ auth_ list classify_account的 cache-auth-list 增强版。- currency_
label - currency enum int → 对齐 currency 标签 (用于 error message)
- default_
currency_ by_ security_ firm - Broker 默认资金视图币种。
- effective_
get_ funds_ currency_ for_ account Trd_GetFunds用户侧 effective currency。- first_
valid_ currency_ for_ account - 真实持仓刷新 CMD3020 使用的默认查询币种。
- known_
currency_ label - Display label for known currency IDs.
- missing_
currency_ error_ message - v1.4.106 Finding F1: missing-currency 错误消息 (Futures / Universal 必传).
对齐 C++
CheckReqParams_GetFunds:475-485“missing necessary parameter Currency” 语义. - parse_
currency_ label - Parse a user-facing currency code into
Trd_Common.Currencyenum int. - single_
currency_ for_ market - 单币种账户的默认 view currency (对齐 C++
INNData_Trd_CommonCurrency.cpp::GetTrdMarketCurrencyline 63-87) - supported_
currencies - 取账户 supported currencies 完整列表 (对齐 C++
INNData_Trd_CommonCurrency::GetAccountValidCurrencyline 90-146) - trade_
read_ currency_ for_ market - 交易读响应的 market → currency 投影。
- unsupported_
error_ message - 把 Unsupported 变 user-friendly error message (PII-free, 不暴露内部 实现细节 / 私仓源码路径 / 发版引用)
- validate_
currency_ for_ account - Layer A pre-check — 严格对齐 C++
CheckReqParams_GetFunds/CheckCurrencyValid(APIServer_Trd_GetFunds.cpp:457-491): - validate_
get_ funds_ currency_ for_ account - User-facing
Trd_GetFundscurrency validation.