BuffMoneyBuffMoney
基础

概念 & 数据模型。

BuffMoney 运行时由 7 个对象组成。每个接入都会碰到前 3 个;其余的我们替你跑。

钱怎么流

  1. 1你的后端每发生一次计量动作,就 POST 一条 usage event。
  2. 2月度 cron 按 (客户, 合同) 聚合事件、锁定一份 FX snapshot。
  3. 3Cron 生成 invoice——标价币种小计、CNY 收款金额。
  4. 4商户或终端用户调收银台接口,我们在微信 / 支付宝侧建一个 payment order。
  5. 5消费者付款。渠道回调到达。我们把 CNY 收款 + FX 换算写入 append-only ledger。
  6. 6月底,财务关闭结算 batch——两位管理员审批后,按结算币种 FX 清算打到你银行。

对象一览

Usage event

一次计量动作——token、agent 调用、图片、GB·天。携带 metric、quantity、customerExternalId、idempotencyKey、occurredAt。

Customer

你的终端用户。我们不处理身份信息,只用你给的 externalId 引用。

Product + rate card

Product 是你卖的东西。Rate card 把 metric → 单位大小 → 单价 minor 绑定。版本化、锁定到 invoice。

Contract

把 (客户, 产品, rate card) 用账期绑起来。Usage events 通过 customer 自动归属合同。

FX snapshot

Invoice 生成时锁定的汇率。同一份 snapshot 用来算 CNY 收款 + USD 净结算。

Invoice

标价币种小计、CNY 收款、平台费、净结算。状态机:draft → finalized → paid(或 void / refunded)。

Payment order

每次 checkout 尝试一条。住在微信或支付宝侧。渠道回调把状态翻成 paid / failed / refunded。

Ledger entry

Append-only 双式记账。每笔交易(收款、平台费、FX、出款)都有匹配的借贷两行。

Settlement batch

按结算币种月度关账。两位管理员审批后,FX 清算电汇到你银行。

不变量

  • 每条业务行都带 merchantId——数据层多租户隔离。
  • 所有金额是 bigint 以字符串序列化,单位是 minor。
  • FX 汇率是 decimal 字符串,不用 JS float。
  • Ledger 分录 append-only;余额 = SUM(credit) − SUM(debit),不 patch。
  • Usage events 用 idempotency key 去重;(merchantId, idempotencyKey) 唯一。