Download OpenAPI specification:
UVS 开放平台标准接入规范与 API 手册。包含 HMAC-SHA256 签名校验、Idempotency-Key 幂等隔离、事件回调 at-least-once 持久化去重规则与二阶段核销链路。
全局集成契约与公共读接口:包含 HMAC-SHA256 签名鉴权、写操作 (POST) 幂等机制(Body 必填 request_id 业务流水号,Header 可选 Idempotency-Key;重试时带相同 Key 安全重放首次响应)、事件回调 at-least-once 幂等去重规则、统一错误码表及通用卡券查询接口 (00.1 POST /v1/coupons/query)。
根据卡券核销码 (code) 查询卡券状态 (ISSUED / LOCKED / REDEEMED / EXPIRED / VOIDED) 及模板信息。需通过与核销相同的授权链:调用方须被授权代理该 merchant,且该 merchant 在券的适用范围内。响应隐去 code,返回卡券外部标识 cpn_…
| coupon required | string 16 位 Crockford Base32 卡券核销码 (code) |
| merchant required | string 发起查询的商户外部 ID (mch_…),须已授权给调用方 Party |
{- "coupon": "164TGDA8HAQ6XS1K",
- "merchant": "mch_7QJ4X2VN8KDA1M5PZR3T"
}{- "ok": true,
- "coupon": {
- "coupon_id": "cpn_998877665544",
- "status": "ISSUED",
- "template_id": "tpl_abc123",
- "batch_id": "bat_xyz789",
- "created_at": "2026-07-26T10:00:00.000Z"
}
}【生命周期 - 起点】发行方/品牌商调用的卡券模板定义、批次制券 (01.1 POST /v1/batches)、批次查询 (01.2 GET /v1/batches/{batchId}) 与批次额度分配 (01.3 POST /v1/batches/allocate)。
当批次异步铸券完成或批次配额划拨给渠道分发方时,系统实时通知 MAKER 或 DISTRIBUTOR。遵循 at-least-once 规则,订阅方必须按 event_id 持久化去重并响应 2xx。
| event_id required | string 事件唯一 ID (evt_…),订阅方持久化去重键 |
| event_type required | string 批次事件类型 (batch.generated / allocation.completed) |
| batch_id required | string 关联的批次外部 ID (bat_…) |
| occurred_at required | string 事件发生时间 (ISO 8601) |
{- "event_id": "evt_bat_12345",
- "event_type": "allocation.completed",
- "batch_id": "bat_20260726_001",
- "occurred_at": "2026-07-26T12:00:00.000Z"
}发行方(Maker)提交批次制券任务,创建 PENDING 批次并进入异步/微批次铸券流程
| idempotency-key | string Example: req_lock_20260726_001 【可选】HTTP 标准写操作幂等 Key。推荐与 Body 中的 request_id 保持一致。超时重试时,带相同 Key 将直接重放首次调用的响应 |
| request_id required | string 【必填】业务操作幂等请求 ID(如 req_batch_001)。重复发送相同 request_id 会安全重放首次调用响应,不会重复制券 |
| template required | string 核销券模板外部 ID (external_id) |
| total_count required | integer > 0 本批次拟制券总张数 |
| distributor | string 预分配的渠道分发方外部 ID (external_id) |
{- "request_id": "req_batch_001",
- "template": "tpl_discount_10",
- "total_count": 1000,
- "distributor": "pty_distributor_01"
}{- "ok": true,
- "batch": {
- "external_id": "bat_20260726_001",
- "status": "PENDING",
- "total_count": 1000,
- "maker_party_id": "pty_maker_01",
- "distributor_party_id": "pty_distributor_01",
- "template_id": "tpl_discount_10",
- "created_at": "2026-07-26T10:00:00.000Z"
}
}发行方(Maker)查询自己名下批次的当前状态 (PENDING / COMPLETED / ALLOCATED) 与配额划拨情况。仅返回请求方自己的批次,他人的批次一律返回 404
| batchId required | string Example: bat_20260726_001 批次外部 ID (bat_…) |
{- "ok": true,
- "batch": {
- "external_id": "bat_20260726_001",
- "status": "PENDING",
- "total_count": 1000,
- "maker_party_id": "pty_maker_01",
- "distributor_party_id": "pty_distributor_01",
- "template_id": "tpl_discount_10",
- "created_at": "2026-07-26T10:00:00.000Z"
}
}发行方(Maker)将已完成铸券的批次整批放行给该批次的分发方以供触达用户。分发方在提交批次时即已确定、出库后不可变,故本接口不接受 distributor 参数
| idempotency-key | string Example: req_lock_20260726_001 【可选】HTTP 标准写操作幂等 Key。推荐与 Body 中的 request_id 保持一致。超时重试时,带相同 Key 将直接重放首次调用的响应 |
| request_id required | string 调用方带入的幂等请求 ID |
| batch required | string 批次外部 ID (bat_…) |
{- "request_id": "req_allocate_001",
- "batch": "bat_20260726_001"
}{- "ok": true,
- "batch": {
- "external_id": "bat_20260726_001",
- "status": "PENDING",
- "total_count": 1000,
- "maker_party_id": "pty_maker_01",
- "distributor_party_id": "pty_distributor_01",
- "template_id": "tpl_discount_10",
- "created_at": "2026-07-26T10:00:00.000Z"
}
}【生命周期 - 流转与结算】分发方/渠道商调用的增量事件拉取 (02.1 GET /v1/events)、对账单列表 (02.2 GET /v1/reconciliations)、CSV 下载 (02.3 GET /v1/reconciliations/{date}/{kind}) 及批次配额划拨接收 (01.3 POST /v1/batches/allocate)。
当卡券发生核销、冲正、过期或作废时,系统实时投递至分发方配置的 webhook_url。遵循 at-least-once 规则,订阅方必须按 event_id 持久化去重并响应 2xx。
| event_id required | string 事件唯一 ID (evt_…),也是订阅方持久化去重键 |
| event_type required | string 事件类型枚举 (coupon.redeemed, coupon.reversed, coupon.expired, coupon.voided) |
| coupon_id required | string 关联的卡券外部 ID (cpn_…) |
| redemption_id required | string or null 关联的核销记录外部 ID (red_…) |
| occurred_at required | string 事件发生时间 (ISO 8601) |
| recorded_at required | string 事件入库记录时间 (ISO 8601) |
{- "event_id": "evt_998877",
- "event_type": "coupon.redeemed",
- "coupon_id": "cpn_998877665544",
- "redemption_id": "red_12345",
- "occurred_at": "2026-07-26T12:00:00.000Z",
- "recorded_at": "2026-07-26T12:00:00.000Z"
}当批次异步铸券完成或批次配额划拨给渠道分发方时,系统实时通知 MAKER 或 DISTRIBUTOR。遵循 at-least-once 规则,订阅方必须按 event_id 持久化去重并响应 2xx。
| event_id required | string 事件唯一 ID (evt_…),订阅方持久化去重键 |
| event_type required | string 批次事件类型 (batch.generated / allocation.completed) |
| batch_id required | string 关联的批次外部 ID (bat_…) |
| occurred_at required | string 事件发生时间 (ISO 8601) |
{- "event_id": "evt_bat_12345",
- "event_type": "allocation.completed",
- "batch_id": "bat_20260726_001",
- "occurred_at": "2026-07-26T12:00:00.000Z"
}当分发方所在时区完成周期日切关账且对账单 CSV 已可下载时,系统投递通知。分发方接收后可调用 GET /v1/reconciliations/{date}/detail 下载 CSV。
| event_id required | string 事件唯一 ID (evt_…),订阅方持久化去重键 |
| event_type required | string 对账事件类型 (reconciliation.ready) |
| business_date required | string 已关账的对账单归属日期 (YYYY-MM-DD) |
| occurred_at required | string 事件发生时间 (ISO 8601) |
{- "event_id": "evt_rec_12345",
- "event_type": "reconciliation.ready",
- "business_date": "2026-07-25",
- "occurred_at": "2026-07-26T00:05:00.000Z"
}分发方(Distributor)按 event_id 游标主动拉取名下的卡券变动事件,用于 Webhook 回调丢失后的补推自愈
| cursor | string Example: cursor=evt_01HZX8... 事件游标,透传上一次拉取返回的 next_cursor |
| limit | string Example: limit=100 单页拉取最大数量(默认 100,上限 1000) |
{- "events": [
- {
- "event_id": "evt_998877",
- "event_type": "coupon.redeemed",
- "coupon_id": "cpn_998877665544",
- "redemption_id": "red_12345",
- "occurred_at": "2026-07-26T12:00:00.000Z",
- "recorded_at": "2026-07-26T12:00:00.000Z"
}
], - "next_cursor": "evt_998899"
}分发方(Distributor)按 business_date 游标拉取已关账的对账单目录与下载 Href
{- "reconciliations": [
- {
- "business_date": "2026-07-25",
- "closed_at": "2026-07-25T23:59:59.000Z",
- "files": [
- {
- "kind": "detail",
- "href": "/v1/reconciliations/2026-07-25/detail"
}
]
}
], - "next_cursor": "2026-07-26"
}分发方下载指定归属日期 (date: YYYY-MM-DD) 的明细对账单 (detail) 或汇总对账单 (summary) CSV 文件
| date required | string Example: 2026-07-25 归属日期 (YYYY-MM-DD) |
| kind required | string Enum: "detail" "summary" Example: detail 文件类型 (detail 明细 / summary 汇总) |
{- "code": "DISCOUNT_NOT_COMPUTABLE",
- "message": "order_amount is required for percentage discount",
- "request_id": "req_8f1b2c3d4e5f",
- "details": null
}【生命周期 - 终点】商户门店 POS 终端调用的卡券核销全链路(03.1 lock 锁定、03.2 redeem 直接核销、03.3 confirm 确认、03.4 cancel 释放、03.5 reverse 冲正、03.6 void 作废、00.1 卡券查询)。
商户 POS 锁定待核销的券,校验离线签名与授权链,计算并返回权威抵扣金额
| idempotency-key | string Example: req_lock_20260726_001 【可选】HTTP 标准写操作幂等 Key。推荐与 Body 中的 request_id 保持一致。超时重试时,带相同 Key 将直接重放首次调用的响应 |
| request_id required | string 【必填】业务操作幂等请求 ID(如 req_20260726_001)。重复发送相同 request_id 会安全重放首次调用响应,不会重复扣款或发动作放 |
| coupon required | string 核销码 (code) |
| merchant required | string 授信商户外部 ID (external_id) |
| store | string 门店外部 ID (external_id) |
| terminal | string POS 终端外部 ID (external_id) |
| order_amount | number 订单总金额(分或元,百分比规则强制要求) |
| currency | string 货币代码 (ISO 4217) |
| order_id | string 外部 POS 订单号 |
{- "request_id": "req_lock_001",
- "coupon": "164TGDA8HAQ6XS1K",
- "merchant": "mch_abc123",
- "store": "sto_store_01",
- "terminal": "trm_pos_01",
- "order_amount": 100,
- "currency": "CNY",
- "order_id": "ORD_20260726_999"
}{- "ok": true,
- "redemption": "red_lock_998877",
- "discount_amount": 15.5
}锁定+确认一次成型,适用于无需预扣校验的即时核销场景
| idempotency-key | string Example: req_lock_20260726_001 【可选】HTTP 标准写操作幂等 Key。推荐与 Body 中的 request_id 保持一致。超时重试时,带相同 Key 将直接重放首次调用的响应 |
| request_id required | string 【必填】业务操作幂等请求 ID(如 req_20260726_001)。重复发送相同 request_id 会安全重放首次调用响应,不会重复扣款或发动作放 |
| coupon required | string 核销码 (code) |
| merchant required | string 授信商户外部 ID (external_id) |
| store | string 门店外部 ID (external_id) |
| terminal | string POS 终端外部 ID (external_id) |
| order_amount | number 订单总金额(分或元,百分比规则强制要求) |
| currency | string 货币代码 (ISO 4217) |
| order_id | string 外部 POS 订单号 |
{- "request_id": "req_lock_001",
- "coupon": "164TGDA8HAQ6XS1K",
- "merchant": "mch_abc123",
- "store": "sto_store_01",
- "terminal": "trm_pos_01",
- "order_amount": 100,
- "currency": "CNY",
- "order_id": "ORD_20260726_999"
}{- "ok": true,
- "redemption": "red_lock_998877",
- "discount_amount": 15.5
}持锁方根据 lock_request_id 最终确认核销扣减
| idempotency-key | string Example: req_lock_20260726_001 【可选】HTTP 标准写操作幂等 Key。推荐与 Body 中的 request_id 保持一致。超时重试时,带相同 Key 将直接重放首次调用的响应 |
| request_id required | string 【必填】业务操作幂等请求 ID。重复发送相同 request_id 会安全重放首次调用响应,不会重复扣款或发动作放 |
| lock_request_id required | string 上一阶段锁定时的 lock_request_id(防越权抢占) |
| coupon required | string 核销码 (code) |
| merchant required | string 授信商户外部 ID (external_id) |
{- "request_id": "req_confirm_001",
- "lock_request_id": "req_lock_001",
- "coupon": "164TGDA8HAQ6XS1K",
- "merchant": "mch_abc123"
}{- "ok": true,
- "redemption": "red_lock_998877",
- "status": "REDEEMED"
}按 (coupon, lock_request_id) 释放预扣锁定
| idempotency-key | string Example: req_lock_20260726_001 【可选】HTTP 标准写操作幂等 Key。推荐与 Body 中的 request_id 保持一致。超时重试时,带相同 Key 将直接重放首次调用的响应 |
| request_id required | string 【必填】业务操作幂等请求 ID。重复发送相同 request_id 会安全重放首次调用响应,不会重复扣款或发动作放 |
| lock_request_id required | string 需要释放的锁定 lock_request_id |
| coupon required | string 核销码 (code) |
{- "request_id": "req_cancel_001",
- "lock_request_id": "req_lock_001",
- "coupon": "164TGDA8HAQ6XS1K"
}{- "ok": true,
- "redemption": "red_lock_998877",
- "status": "REDEEMED"
}对已完成的核销记录进行全额冲正并写流水账本
| idempotency-key | string Example: req_lock_20260726_001 【可选】HTTP 标准写操作幂等 Key。推荐与 Body 中的 request_id 保持一致。超时重试时,带相同 Key 将直接重放首次调用的响应 |
| request_id required | string 【必填】业务操作幂等请求 ID。重复发送相同 request_id 会安全重放首次调用响应,不会重复扣款或发动作放 |
| redemption required | string 待冲正的核销记录外部 ID (red_…) |
| reason | string 冲正/退款原因说明 |
{- "request_id": "req_reverse_001",
- "redemption": "red_lock_998877",
- "reason": "顾客退货撤销交易"
}{- "ok": true,
- "redemption": "red_lock_998877",
- "reversal": "rvs_00112233",
- "status": "REVERSED"
}作废未使用的合规卡券(CREATED / ISSUED)
| idempotency-key | string Example: req_lock_20260726_001 【可选】HTTP 标准写操作幂等 Key。推荐与 Body 中的 request_id 保持一致。超时重试时,带相同 Key 将直接重放首次调用的响应 |
| request_id required | string 【必填】业务操作幂等请求 ID。重复发送相同 request_id 会安全重放首次调用响应,不会重复扣款或发动作放 |
| coupon required | string 待作废的核销码 (code) |
| merchant required | string 授信商户外部 ID (external_id) |
| reason | string 作废原因说明 |
{- "request_id": "req_void_001",
- "coupon": "164TGDA8HAQ6XS1K",
- "merchant": "mch_abc123",
- "reason": "活动作废退款"
}{- "ok": true,
- "coupon_id": "cpn_998877665544",
- "status": "VOIDED"
}根据卡券核销码 (code) 查询卡券状态 (ISSUED / LOCKED / REDEEMED / EXPIRED / VOIDED) 及模板信息。需通过与核销相同的授权链:调用方须被授权代理该 merchant,且该 merchant 在券的适用范围内。响应隐去 code,返回卡券外部标识 cpn_…
| coupon required | string 16 位 Crockford Base32 卡券核销码 (code) |
| merchant required | string 发起查询的商户外部 ID (mch_…),须已授权给调用方 Party |
{- "coupon": "164TGDA8HAQ6XS1K",
- "merchant": "mch_7QJ4X2VN8KDA1M5PZR3T"
}{- "ok": true,
- "coupon": {
- "coupon_id": "cpn_998877665544",
- "status": "ISSUED",
- "template_id": "tpl_abc123",
- "batch_id": "bat_xyz789",
- "created_at": "2026-07-26T10:00:00.000Z"
}
}【回调与离线自愈】当卡券状态变更 (04.1 coupon.event)、批次铸券完成与放行 (04.2 batch.event) 或对账单就绪 (04.3 reconciliation.event) 时,系统主动推送到订阅方 webhook_url。遵循 at-least-once 规则,订阅方必须按 event_id 持久化去重并响应 HTTP 2xx。
当卡券发生核销、冲正、过期或作废时,系统实时投递至分发方配置的 webhook_url。遵循 at-least-once 规则,订阅方必须按 event_id 持久化去重并响应 2xx。
| event_id required | string 事件唯一 ID (evt_…),也是订阅方持久化去重键 |
| event_type required | string 事件类型枚举 (coupon.redeemed, coupon.reversed, coupon.expired, coupon.voided) |
| coupon_id required | string 关联的卡券外部 ID (cpn_…) |
| redemption_id required | string or null 关联的核销记录外部 ID (red_…) |
| occurred_at required | string 事件发生时间 (ISO 8601) |
| recorded_at required | string 事件入库记录时间 (ISO 8601) |
{- "event_id": "evt_998877",
- "event_type": "coupon.redeemed",
- "coupon_id": "cpn_998877665544",
- "redemption_id": "red_12345",
- "occurred_at": "2026-07-26T12:00:00.000Z",
- "recorded_at": "2026-07-26T12:00:00.000Z"
}当批次异步铸券完成或批次配额划拨给渠道分发方时,系统实时通知 MAKER 或 DISTRIBUTOR。遵循 at-least-once 规则,订阅方必须按 event_id 持久化去重并响应 2xx。
| event_id required | string 事件唯一 ID (evt_…),订阅方持久化去重键 |
| event_type required | string 批次事件类型 (batch.generated / allocation.completed) |
| batch_id required | string 关联的批次外部 ID (bat_…) |
| occurred_at required | string 事件发生时间 (ISO 8601) |
{- "event_id": "evt_bat_12345",
- "event_type": "allocation.completed",
- "batch_id": "bat_20260726_001",
- "occurred_at": "2026-07-26T12:00:00.000Z"
}当分发方所在时区完成周期日切关账且对账单 CSV 已可下载时,系统投递通知。分发方接收后可调用 GET /v1/reconciliations/{date}/detail 下载 CSV。
| event_id required | string 事件唯一 ID (evt_…),订阅方持久化去重键 |
| event_type required | string 对账事件类型 (reconciliation.ready) |
| business_date required | string 已关账的对账单归属日期 (YYYY-MM-DD) |
| occurred_at required | string 事件发生时间 (ISO 8601) |
{- "event_id": "evt_rec_12345",
- "event_type": "reconciliation.ready",
- "business_date": "2026-07-25",
- "occurred_at": "2026-07-26T00:05:00.000Z"
}