Files
cpa-plugin/docs/modules/data.md
T

20 KiB
Raw Blame History

数据模块

1. 定位

数据模块是 cpa-ext 的统一数据语言。它只回答三件事:

  1. 系统需要从 CLIProxyAPI(CPA)及相关来源关注什么数据;
  2. 这些数据在插件内部以什么稳定语义流转;
  3. 计费、统计、Key 管理、配额、审计和展示模块可以得到什么输出。

数据模块不负责采集回调、计算费用、执行扣款、生成统计图或决定界面权限。具体模块负责产生和消费数据,数据模块只定义契约。

本模块以两个已经实际工作的项目为需求来源:

  • cpa-plugin-key-billing 已经拿到并使用的数据,全部视为我们需要关注的数据;
  • cpa-usage-keeper 已经拿到并使用的数据,全部视为我们需要关注的数据;
  • 两者已经对外提供的数据产品,全部纳入我们的输出能力全集;
  • 第一版可以只实现其中一部分,但数据抽象不能阻止以后补齐其余能力。

2. 两个参考项目的数据总结

2.1 cpa-plugin-key-billing

它拿到的数据

数据域 实际取得的内容 主要来源
下游调用身份 caller_scope、Key 脱敏预览、标签、Key 是否仍在 CPA 配置中 请求 metadata、管理端同步的 CPA Key 列表
请求关联 request_id、入口 endpoint、请求格式、上游格式、流式标记、是否真实生成 request interceptor、request lifecycle
模型 用户/路由模型、实际上游模型、稳定 billing model 请求阶段、响应阶段
上游凭证 auth_index、provider、auth type、OAuth 账户或脱敏 provider API Key CPA usage callback
请求终态 正常、失败、取消、拒绝 request lifecycle
原始用量 OpenAI/Codex、Claude、Gemini、Interactions 等响应中的 usage 和 response ID 翻译前响应、非流式响应、流式 chunk
标准 Token 非缓存输入、缓存读取、缓存写入、普通输出、推理输出、总量、无法分类数量 自身规范化逻辑
数据质量 complete、inconsistent、unclassified、未观察到用量 自身规范化逻辑
价格 模型匹配规则、每百万 Token 各分项价格、长上下文门槛与价格、价格来源 内置 models.dev 目录、管理员覆盖
套餐与周期 套餐 ID/名称、美元额度、日/周/月/自定义周期、周期开始与结束 插件配置与持久化状态
请求准入快照 请求进入时绑定的 Key、套餐和周期 请求 interceptor

它没有把 CPA 的 usage_plugin 当作完整用量事实:该回调缺少 RequestID,所以项目主要从带有请求关联信息的响应 hook 中恢复权威 Token,再在终态回调结算;usage_plugin 主要用来补充上游凭证身份。

它存储的数据

  • 价格规则、套餐、Key 状态、上游凭证目录;
  • Key 的当前周期和生命周期累计;
  • 按模型累计;
  • 最近 30 天请求日志;
  • 每次请求的标准 Token、金额分项、价格来源、长上下文状态和数据质量;
  • 运行时未定价、无 Token、无法分类等诊断计数。

它输出的数据

输出域 已提供的数据
请求控制 放行或拒绝,额度耗尽时返回明确的 HTTP 错误
Key 目录 Key 标识/预览/标签、套餐、是否无限、是否阻断、周期额度、已用、使用率、周期结束时间
套餐管理 套餐及金额、周期,绑定、解绑和重置
请求账目 时间、Key、请求 ID、endpoint、上游凭证、模型、结果、Token、金额、价格来源和核算质量
汇总 Key 数量、阻断数量、生命周期请求/Token/金额、按模型汇总
价格管理 当前模型价格、自定义覆盖、价格刷新结果
运维诊断 持久化状态、配置状态、未定价/缺失/无法分类计数

2.2 cpa-usage-keeper

它拿到的数据

数据域 实际取得的内容 主要来源
用量事件 provider、endpoint、auth type/index、request ID、API Key、模型/别名、请求与响应 service tier、reasoning effort、executor、时间、失败、延迟、TTFT、完整 Token 分项 CPA Redis usage queue / HTTP usage queue
请求环境 client IP、X-Forwarded-For、User-Agent、source、API group key CPA usage payload
下游 Key 完整 CPA API Key、展示值、别名、删除/同步状态 CPA Management API
上游 Auth File auth index、名称、文件、email、provider、label、状态、priority、disabled、note、account/project、订阅起止与 plan type CPA Management API
Provider API Key 配置 provider 类型、名称、prefix、base URL、lookup key 等归一化元数据 CPA 各 provider management API
模型目录 模型 ID、owner、创建时间 CPA /v1/models
上游配额 Codex 主/次窗口、允许状态、使用率、重置时间、额外限制、reset credits;以及其他 provider 的 quota CPA 代调用各 provider API
上游订阅 Codex plan、tier、有效期;其他 provider 的订阅/账户资料 auth metadata、provider API
请求日志 按 request ID 获取的请求日志、预览与下载数据 CPA request-log management API
价格 模型价格快照、条件规则、service tier、reasoning、模型、Key、auth、endpoint、executor 等价格维度 models.dev、管理员配置

它存储的数据

  • 原始 Redis inbox 及处理/重试状态;
  • 标准化的逐次用量事件和归档;
  • CPA API Key 与上游身份目录;
  • 模型价格设置、同步快照和条件价格规则;
  • 小时/日 overview、activity、latency、identity 等预聚合及各自 checkpoint
  • 配额快照和应用设置;
  • 排名等派生结果。

它输出的数据

输出域 已提供的数据
Overview 请求数、Token、金额、RPM、TPM、日均值、缓存命中率和时间序列
实时状态 Token 速度、请求速度、TTFT/Latency P50/P95、响应分布、当前模型/Key/Auth Top、缓存水平
事件明细 可分页筛选的逐请求记录,包含模型、身份、结果、Token、金额、延迟和请求日志入口
Analysis Token 时序、模型使用、Key/模型/Auth 构成、Key×模型热力图、金额分项、模型效率
Activity 日/周/月/年活动格、成功失败、成功率和各 Token 分项
身份目录 下游 Key 与上游账号/provider 的元数据、别名、启停状态、订阅和累计使用情况
配额 各上游账号的窗口、使用率、剩余、重置时间、订阅层级和 reset credits
价格 当前价格、价格来源、同步状态、条件规则及预览
排名与导出 本地排名、事件导出、请求日志查看/下载

3. 我们的数据关注全集

两个项目的数据取并集后,数据模块定义以下九个数据域。这里的“需要”表示契约需要容纳,不表示所有字段都必须在 MVP 首日采集完成。

3.1 请求与执行

必须同时表达两个层级:

  • Request:一次下游用户请求;
  • Execution:一次 CPA after-auth 可观察到的上游逻辑执行段。

一个 Request 可以因为重试、故障切换或路由产生多个 Execution。Execution 不保证等于一个物理 HTTP dispatch:当前 CPA 在 auth refresh 后的内部重发不会再次触发 after-auth,应以 subattempt_count/observability=partial 表达,而不是伪造额外 Execution。未来宿主提供 dispatch lifecycle 时再增加 DispatchAttempt

关注字段:

  • request/event/trace/execution ID
  • endpoint、source、source format、upstream format
  • requested model、routed model、upstream model、model alias
  • stream、generate、reasoning effort
  • requested、reported、effective service tier
  • requested、started、first-token、completed 时间;
  • outcome、HTTP status、标准错误类别;
  • settlement status(与请求 outcome 分开,允许 canceled/failed 请求在迟到 Usage 后结算);
  • latency、TTFT
  • 重试序号及最终尝试标记。

3.2 下游身份

关注字段:

  • account/member ID
  • credential ID
  • credential secret version/public ID/HMAC key ID/status
  • 自管 Key 的 public key ID、HMAC digest、digest secret version
  • CPA 根据 Principal 派生的稳定 caller scope(仅用于请求期关联,不作为业务主键);
  • 兼容模式下 CPA 原生 API Key 的稳定 scope/hash
  • 脱敏预览、别名、标签;
  • 启用、删除、同步状态;
  • 套餐/计费账户绑定。

自管 Key 的完整值只在创建/轮换成功时展示一次,持久层只保存摘要;CPA 原生 Key 即使在兼容迁移模式由 CPA 配置持有,也不得复制进插件事件、日志或跨模块消息。

3.3 上游身份

关注字段:

  • auth ID/index/type
  • provider、executor type
  • 名称、别名、email/account、文件标识;
  • provider prefix、base URL、lookup key
  • priority、disabled、status、note
  • account/project ID
  • plan/tier 和订阅有效期。

秘密凭证不属于数据流转契约。

3.4 用量

统一为互不重叠、跨 provider 可比较的字段:

  • uncached input
  • cache read
  • cache creation/write
  • non-reasoning output
  • reasoning output
  • total
  • unclassified
  • generate 标记。

同时保留规范化质量:completenormalizedpartialinconsistentunclassifiedmissing,以及修正动作/异常代码。原始 provider 计数可以作为受限审计快照保存,但不能直接成为跨模块语义。

3.5 金额与价格

关注字段:

  • settlement currency
  • 金额的定点整数值;
  • 未缓存输入、缓存读取、缓存写入、输出的金额分项;
  • base amount、final charged amount
  • 每百万 Token 的实际应用价格;
  • service tier / Fast multiplier
  • 长上下文门槛及是否命中;
  • price version、source、effective time
  • 价格是否可用及不可用原因;
  • billing record ID、request/execution ID、usage revision
  • charge、late settlement、credit、refund、adjustment 类型及被修正记录;
  • pending/awaiting usage/settled/unmeasured/inconsistent 状态;
  • occurred at 与 booked at。

用户侧核心金额只使用最终结算金额;Token、价格与倍率是后台审计数据。

3.6 下游套餐、周期与余额

关注字段:

  • plan、额度金额和周期规则;
  • BillingAccount 与 plan 的绑定、Credential → BillingAccount 绑定;
  • cycle start/end
  • limit、spent、remaining
  • blocked/allowed
  • 管理员调整及其原因;
  • 请求准入时使用的周期快照。

3.7 上游配额与订阅

它和我们分配给用户的金额额度是不同概念,必须分开表达。

关注字段:

  • provider/account
  • plan/tier、订阅起止;
  • primary/secondary/additional windows
  • used、limit、remaining、percentage
  • allowed、limit reached
  • window duration、reset at/after
  • window usage token/cost
  • reset credit 数量、状态和过期时间;
  • snapshot time 和数据新鲜度。

3.8 模型、价格与配置目录

关注字段:

  • CPA 可用模型及 owner
  • 模型别名和路由映射;
  • provider/model 对应关系;
  • 价格目录、管理员覆盖和条件规则;
  • Key、auth、provider 的当前配置事实;
  • 同步时间、来源、版本和删除状态。

3.9 诊断、日志与数据质量

关注字段:

  • schema version、producer version
  • source/provenance、observed at、persisted at
  • idempotency key
  • 缺失、修正、冲突、未定价状态;
  • inbox/checkpoint/retry/archive 状态;
  • 请求日志引用和受控下载信息;
  • 原始数据哈希或受限审计引用。

Prompt、模型完整响应、Authorization、Cookie、OAuth token 和 provider API Key 默认不进入通用数据契约。

4. 核心抽象

数据模块不要求所有内容塞进一张表。它定义以下稳定对象,存储模块可以分别落库。

DownstreamAccount
  └─ BillingAccount
       └─ DownstreamCredential (1..N)
            ├─ CredentialSecretVersion (1..N)
            └─ Request
                 └─ Execution (1..N)
                      ├─ Usage
                      ├─ Outcome & Performance
                      └─ UpstreamIdentity

Usage + PricingSnapshot
  └─ BillingRecord
       └─ LedgerEntry

Usage / BillingRecord / Identity / QuotaSnapshot
  └─ Aggregate & View

4.1 RequestRecord

用户视角的一次请求。保存下游身份、入口、请求模型、最终结果、时间以及所有 Execution 的关联,不直接猜测每次上游尝试的细节。

4.2 ExecutionRecord

一次 CPA after-auth 可观察到的逻辑执行段。保存上游凭证、provider、实际模型、tier、格式、终态、性能、重试关系和 observability;不能宣称等于每个物理 HTTP dispatch。

4.3 UsageRecord

一次 Execution 对应的标准 Token 事实,包含质量和来源。Request 层用量由明确规则合并,不覆盖底层执行事实。当前 CPA 对部分 Usage 缺少 RequestID/AttemptID,无法可靠归属时必须保持 unmeasured/未关联事实,不能按时间或上游账户猜配。

4.4 BillingRecord

计费模块对 Usage 应用价格后产生的不可变金额事实。它引用 Usage revision 和价格快照,迟到结算、退款或人工修正通过新增记录表达;金额一旦入账,统计模块不得重新计算并改写历史。

4.5 IdentityRecord

统一承载下游 Key/账户和上游 auth/provider 的非秘密身份信息,但通过明确的 identity kind 区分,不能只靠一个字符串猜类型。

4.6 QuotaSnapshot

某个上游身份在某一时刻的 provider 配额和订阅快照。它是时间点事实,不覆盖历史;也不与下游金额余额混用。

4.7 CatalogSnapshot

模型、价格、路由和配置目录的带版本快照,使历史请求可以解释当时使用的模型和价格。

4.8 AggregateRecord

从不可变事实派生的小时、日、活动、延迟、身份和排名数据。它可以删除并重建,不是账本真相。

4.9 ProjectionEvent

跨 Request、Usage、Billing、Ledger 多表的统一追加变化流。它携带单调 event_seq、唯一 event_id、kind、fact ID/revision、occurred/booked time、可选 supersedes ID 和确定性统计差量。领域事实与对应 ProjectionEvent 必须在同一事务提交;统计 projector 只按这条流推进,不能比较各表互不相关的自增 ID。

5. 统一数据元信息

所有可持久化的事实对象都应携带或可追溯到:

字段 含义
schema_version 数据契约版本
event_id 全局稳定事件 ID
idempotency_key 重复回调或重放时去重
source CPA callback、response hook、Redis、Management API、provider API 等
observed_at 来源数据被观察到的时间
occurred_at 业务事实真实发生时间
persisted_at 成功落库时间
quality 完整、修正、部分、矛盾、缺失等
producer_version 产生该规范化数据的插件版本

字段缺失必须保持“未知”,不能自动等价为零、空字符串或成功。

6. 数据模块输出契约

数据模块定义四类输出,具体模块按需实现和消费。

6.1 事实输出

  • Request、Execution、Usage、Billing、Ledger、ProjectionEvent
  • Downstream/Upstream Identity
  • Quota、Subscription、Catalog 快照;
  • 数据质量和诊断事件。

6.2 查询输出

  • 逐请求和逐执行明细;
  • Key、账户、上游身份、模型和价格目录;
  • 套餐、周期、余额和账本;
  • 配额、订阅和重置时间;
  • 请求日志的受控引用。

6.3 聚合输出

完整能力集合至少容纳:

  • 请求、Token、金额、RPM、TPM
  • 时间序列和日均;
  • 成功率、错误分布;
  • TTFT/Latency 分位数和分布;
  • 缓存读取率;
  • 模型、Key、账户、Auth、Provider 构成及 Top
  • Key×模型热力图;
  • 金额分项和模型效率;
  • 活动格、排名和历史对比。

6.4 控制输出

  • 请求允许/拒绝及稳定错误码;
  • Key、套餐、价格和绑定的变更结果;
  • 配额刷新/重置结果;
  • 同步、归档、重建和诊断结果。

控制输出由业务模块决定,数据模块只定义其可交换的数据形状。

7. 模块边界

模块 对数据模块的关系
CPA 适配层 把 CPA 回调、响应和 Management API 数据翻译成标准事实
存储模块 按契约持久化、查询、去重、归档和迁移
Core/Key 模块 维护下游身份、金额账户和绑定关系
上游账户模块 维护 CPA Auth 引用、priority、bindability 和 Quota/Subscription 快照
价格模块 维护不可变 PriceVersion、模型 alias 和计价政策
计费模块 消费 Usage、Pricing、Plan,输出 Billing 和 Ledger
统计模块 消费不可变事实,输出可重建的 Aggregate
API/UI 模块 将同一数据按用户或管理员权限投影,不发明新的业务事实

数据模块自身:

  • 不依赖 UI
  • 不依赖某一种数据库;
  • 不调用 CPA
  • 不计算价格;
  • 不聚合统计;
  • 不保存或传播秘密;
  • 不把参考项目现有字段名直接当成永久领域语义。

8. 如何参考两个项目

8.1 从 cpa-plugin-key-billing 参考

重点查看:

  • internal/plugin/usage_tracker.go:请求与响应用量关联;
  • internal/plugin/upstream_usage.go:跨 provider Token 语义;
  • internal/billing/pricing.go:标准 Token、数据质量、价格和金额分项;
  • internal/billing/account.go:终态用量到费用记录;
  • internal/billing/state.go:价格、套餐、Key、周期、累计和日志;
  • internal/billing/log.gokeys.go:请求账目和管理输出;
  • internal/billing/credentials.go:上游凭证的安全展示身份。

吸收它对请求关联、Token 不重叠、质量显式化、请求准入周期快照和上游身份脱敏的定义;不要继承其 JSON 大状态、浮点余额、30 天日志限制和把重试只保留为最终 provider usage 的数据损失。

8.2 从 cpa-usage-keeper 参考

重点查看:

  • internal/entities/usage_event.go:逐请求事件字段;
  • internal/entities/usage_identity.gocpa_api_key.go:身份目录;
  • internal/service/sync.go:用量规范化、来源和 inbox 处理;
  • internal/service/tokenprocessor/Token 修正与质量判断;
  • internal/pricing/internal/entities/model_price_*:价格快照与条件;
  • internal/quota/:上游配额、订阅和 provider 抽象;
  • internal/service/dto/usage.goanalysis.gousage_activity.go:查询和分析输出;
  • internal/repository/usage*.go:明细、聚合、checkpoint 和归档。

吸收它完整的事件、身份、配额、价格、实时和分析数据面;不要把其 Redis/HTTP 拉取方式、明文 CPA Key 存储方式、GORM 实体或动态历史费用重算直接变成我们的领域契约。

9. 本模块的完成标准

  • 两个参考项目实际使用的输入数据均能映射到本模块的数据域;
  • 两个参考项目实际提供的输出均能由本模块的事实或派生数据表达;
  • Request 与 Execution、下游额度与上游配额、Usage 与 Billing、事实与聚合均明确分离;
  • 未知、缺失、零和失败具有不同语义;
  • 所有金额可使用定点整数,所有历史收费可追溯到价格快照;
  • 所有秘密字段均被排除或明确限定在受保护配置边界;
  • 后续模块只能扩展契约版本,不能用自己的私有字段重新定义同一个业务事实。