channel_monitor_quota.go 3.5 KB

1234567891011121314151617181920212223242526272829303132333435363738394041424344454647484950515253545556575859606162636465666768
  1. package domain
  2. import "time"
  3. // 渠道监控「配额模式」的归一化配额快照类型。
  4. //
  5. // 配额模式监控不直接对接上游,而是关联一个已有账号,复用账号侧的用量服务
  6. // (AccountUsageService / CNProviderQuotaService / CNProviderBalanceService),
  7. // 把各平台形态各异的用量数据归一成 MonitorQuotaSnapshot,随检测历史持久化
  8. // 到 channel_monitor_histories.quota(JSONB),供管理端与用户端渲染。
  9. //
  10. // 类型放在 domain 包是因为 ent schema(internal/domain 的下游)需要引用它做
  11. // field.JSON 序列化;service 不能被 ent import(会造成循环依赖)。
  12. // MonitorQuotaTier 单个用量窗口的快照。
  13. //
  14. // Window 取值约定(与前端 monitorCommon.quota.windows.* 标签一一对应):
  15. // - "5h" 5 小时滚动窗口(Claude/Codex/Kimi/Zhipu coding plan)
  16. // - "7d" 7 天窗口(Claude/Codex)
  17. // - "7d-sonnet" Claude 7 天 Sonnet 独立额度
  18. // - "7d-fable" Claude 7 天 Fable 独立额度
  19. // - "weekly" 周窗口(Kimi/Zhipu coding plan)
  20. // - "daily" 日窗口(Gemini 日配额 / Grok 日请求)
  21. // - "30d" 30 天窗口(Grok 月度)
  22. // - "total" 无窗口语义的总量额度(Antigravity per-model 等)
  23. //
  24. // 同一 Window 可能出现多条(Gemini 多档日配额、Antigravity per-model、
  25. // Grok requests/tokens),用 Label 区分:Label 是机器 token(requests/tokens/
  26. // shared/pro/flash 或模型名),前端已知 token 走 i18n,未知原样展示。
  27. type MonitorQuotaTier struct {
  28. Window string `json:"window"`
  29. Label string `json:"label,omitempty"`
  30. UsedPercent float64 `json:"used_percent"` // 0-100+;仅有绝对值时按 used/limit 计算
  31. Used float64 `json:"used,omitempty"`
  32. Limit float64 `json:"limit,omitempty"`
  33. ResetAt string `json:"reset_at,omitempty"` // RFC3339;未知时留空
  34. }
  35. // MonitorQuotaSnapshot 一次配额查询的完整快照。
  36. //
  37. // Source 取值:
  38. // - "usage" 海外平台(AccountUsageService.GetUsage)
  39. // - "cn_quota" 国产 Coding Plan(CNProviderQuotaService.QueryUsage)
  40. // - "cn_balance" 国产按量付费余额(CNProviderBalanceService.QueryBalance)
  41. type MonitorQuotaSnapshot struct {
  42. Source string `json:"source"`
  43. Success bool `json:"success"`
  44. Tiers []MonitorQuotaTier `json:"tiers,omitempty"`
  45. Balance *float64 `json:"balance,omitempty"` // cn_balance 主余额
  46. Balances []MonitorBalance `json:"balances,omitempty"` // 多币种余额(如 DeepSeek CNY+USD)
  47. Currency string `json:"currency,omitempty"` // 主余额币种
  48. PlanLevel string `json:"plan_level,omitempty"` // 套餐等级(如智谱 level)
  49. // BalanceLow 余额低于阈值或账号被上游标记不可用(仅 cn_balance 来源)。
  50. // 抓取器按 Gateway.CNProviders.BalanceThreshold 判定,口径与账号停调
  51. // (CNProviderBalanceCheckService.checkOne)一致:任一币种达标即健康。
  52. BalanceLow bool `json:"balance_low,omitempty"`
  53. // CredentialInvalid 上游 401/403 鉴权失败(区别于网络/解析错误),
  54. // 检测状态据此推导 failed 而非 error。
  55. CredentialInvalid bool `json:"credential_invalid,omitempty"`
  56. Error string `json:"error,omitempty"` // Success=false 时的错误摘要
  57. FetchedAt time.Time `json:"fetched_at"`
  58. }
  59. // MonitorBalance 单币种余额条目。
  60. type MonitorBalance struct {
  61. Currency string `json:"currency"`
  62. Balance float64 `json:"balance"`
  63. }