﻿# 适用场景

即刻收面向承载创作者、应用或数字服务的平台，提供收费配置、托管购买、权益查询和额度核销能力。平台通过支付宝 OpenAPI 为创作者接入收费：创作者在支付宝托管页完成收费配置，用户在托管购买页支付，平台服务端根据权益或核销结果开放服务。

## 支持的收费模式

| 收费模式 | billing_mode | 权益或额度 | 平台使用方式 | 重复购买 |
| --- | --- | --- | --- | --- |
| 永久买断 | `ONE_TIME` | 永久使用权益 | 使用前查询访问决策 | 已有有效权益时不再购买 |
| 时长包 | `ONE_TIME_DURATION` | 固定有效期权益 | 使用前查询访问决策，可展示有效期 | 有效期内不续购；到期后按查询结果购买 |
| 次数包 | `QUANTITY`，`quota_unit=COUNT` | 可消耗次数 | 查询余额，每次服务按约定数量核销 | 可加购，新增额度累加 |
| 积分包 | `QUANTITY`，`quota_unit=POINT` | 可消耗积分 | 查询余额，按服务规则核销积分 | 可加购，新增额度累加 |

同一商品最终采用一种收费模式，该模式下可配置多个档位。例如，次数包可提供“20 次包”和“100 次包”，用户购买后增加相应次数。

时长包支持以下周期，按日历计算，不能将“一个月”固定换算成 30 天：

| duration_period | 对客名称 | 计算口径 |
| --- | --- | --- |
| `WEEK` | 一周 | 按日历增加 1 周 |
| `MONTH` | 一个月 | 按日历增加 1 个月 |
| `QUARTER` | 三个月 | 按日历增加 3 个月 |
| `YEAR` | 一年 | 按日历增加 1 年 |

本接入范围支持买断、固定周期时长包和次数／积分额度包，不包含自动续费、任意天数、有效期内时长续购、商品改价、核销撤销。

# 接入准备

## 平台与支付宝的职责

| 参与方 | 负责内容 |
| --- | --- |
| 平台服务端 | 维护商品、创作者及用户标识；签名调用接口；保存幂等请求；根据权益与核销结果控制服务 |
| 平台客户端 | 展示收费状态、档位和余额；打开接口返回的托管页面或展示二维码；页面返回后触发服务端查询 |
| 创作者 | 在支付宝托管页完成所需账号绑定、收费模式与档位配置，管理商品收费状态 |
| 即刻收 | 提供配置和购买入口、支付与权益处理、权益查询及额度扣减结果 |

## 开始前完成以下准备

1. 准备平台的支付宝应用 `app_id`、应用私钥和对应支付宝公钥，并完成所需接口权限及平台接入配置。
2. 在平台服务端接入支付宝服务端 SDK，配置签名与验签。请求网关为 `https://openapi.alipay.com/gateway.do`，API 版本为 `1.0`，推荐使用 `RSA2`、`UTF-8` 和 JSON。
3. 确定商品、创作者和权益受益人的稳定标识，建立商品归属与平台登录用户的对应关系。

OpenAPI 凭证保存在平台服务端。平台服务端根据已登录用户及商品归属确定身份参数，不能直接信任客户端任意传入的创作者或受益人标识。

# 手动集成

## 第一步：为创作者配置收费

### 系统流程

```mermaid
sequenceDiagram
    autonumber
    participant C as 创作者
    participant P as 平台
    participant N as 即刻收 OpenAPI
    participant H as 支付宝托管配置页
    C->>P: 进入商品收费设置
    P->>N: alipay.aipay.nowpay.charge.query
    N-->>P: capability_status / management_url
    alt NOT_CONFIGURED 或 CONFIGURING
        P->>N: alipay.aipay.nowpay.charge.initialize
        N-->>P: configuration_url / configuration_qr_code
        P-->>C: 展示配置入口
        C->>H: 打开配置页并完成收费设置
        H-->>P: 返回 callback_url
    else 已配置状态
        P-->>C: 展示 management_url
        C->>H: 进入商品管理
    end
    P->>N: alipay.aipay.nowpay.charge.query
    N-->>P: 最新状态、收费模式与档位
```

1. 调用 [alipay.aipay.nowpay.charge.query（查询收费能力和档位）](api-list/alipay_aipay_nowpay_charge_query.md)，传入平台商品和创作者标识。
2. 当 `capability_status` 为 `NOT_CONFIGURED` 或 `CONFIGURING` 时，调用 [alipay.aipay.nowpay.charge.initialize（初始化收费配置）](api-list/alipay_aipay_nowpay_charge_initialize.md)，使用返回的配置链接或二维码引导创作者完成设置。
3. 当状态为 `PENDING`、`ACTION_REQUIRED`、`ENABLED`、`DISABLED` 或 `TERMINATED` 时，使用查询返回的 `management_url` 进入管理页，查看进度或处理商品。
4. 页面返回或创作者主动刷新时，再次查询收费能力。只有 `ENABLED` 表示商品允许新增购买。

初始化请求的 `biz_content` 示例：

```json
{
  "out_product_id": "app_writing_001",
  "external_owner_id": "creator_001",
  "product_name": "智能写作助手",
  "product_icon_url": "https://platform.example.com/assets/writing.png",
  "product_url": "https://platform.example.com/apps/app_writing_001",
  "callback_url": "https://platform.example.com/nowpay/config-return",
  "pricing_mode_list": [
    {
      "billing_mode": "QUANTITY",
      "quota_unit": "COUNT"
    }
  ]
}
```

本例提示配置次数包。初始化不传价格；创作者在托管页选择收费方式并配置档位。商品配置成功后，平台从 `alipay.aipay.nowpay.charge.query` 读取实际 `billing_mode`、`quota_unit`、`charging_options`。

若重复初始化返回 `NOW_PAY_ALREADY_CONFIGURED`，调用 `alipay.aipay.nowpay.charge.query` 获取管理入口。不要依赖失败响应返回链接，也不要将初始化成功当作商品已经上架。

### 收费状态与页面处理

| capability_status | 商品含义 | 平台页面处理 |
| --- | --- | --- |
| `NOT_CONFIGURED` | 尚未初始化 | 展示“设置收费”，点击后调用初始化接口 |
| `CONFIGURING` | 配置尚未完成 | 展示“继续配置”，复用原申请进入配置页 |
| `PENDING` | 等待审核或发布 | 使用管理入口查看进度 |
| `ACTION_REQUIRED` | 需要创作者处理 | 使用管理入口完成处理 |
| `ENABLED` | 允许新增购买 | 展示用户购买入口与商品管理入口 |
| `DISABLED` | 已停止新增购买 | 隐藏新购买入口；已有权益继续按权益接口判断 |
| `TERMINATED` | 商品已归档 | 使用管理入口查看状态，不新增购买 |

商品收费状态与某个用户的权益状态分别查询。商品已停用不能直接推断用户已有权益失效；商品已启用也不能直接推断用户已有访问权限。

## 第二步：按收费模式选择流程

| billing_mode | 使用前查询 | 需要购买时 | 支付页面返回后 | 实际消费时 |
| --- | --- | --- | --- | --- |
| `ONE_TIME` | alipay.aipay.nowpay.purchase.consult | 使用 alipay.aipay.nowpay.purchase.consult 返回的购买入口，或通过 alipay.aipay.nowpay.purchase.create 选择指定档位 | 再查 alipay.aipay.nowpay.purchase.consult | 按访问决策放行 |
| `ONE_TIME_DURATION` | alipay.aipay.nowpay.purchase.consult | 同上 | 再查 alipay.aipay.nowpay.purchase.consult，读取当前有效期 | 按访问决策放行 |
| `QUANTITY` | alipay.aipay.nowpay.quota.query | alipay.aipay.nowpay.purchase.create | 再查 alipay.aipay.nowpay.quota.query | alipay.aipay.nowpay.quota.verify；结果未知用 alipay.aipay.nowpay.quota.refresh |

### 买断和时长包

```mermaid
sequenceDiagram
    autonumber
    participant U as 用户
    participant P as 平台
    participant N as 即刻收 OpenAPI
    participant H as 支付宝托管购买页
    U->>P: 使用付费功能
    P->>N: alipay.aipay.nowpay.purchase.consult
    N-->>P: decision
    alt ALLOW
        P-->>U: 开放服务
    else PURCHASE_REQUIRED
        P-->>U: 展示购买入口
        U->>H: 选择档位并支付
        H-->>P: 返回 callback_url
        P->>N: alipay.aipay.nowpay.purchase.consult
        N-->>P: 最新 decision
        P-->>U: 按查询结果开放服务或提示刷新
    else DENY
        P-->>U: 不开放服务，按原因展示说明
    end
```

调用 [alipay.aipay.nowpay.purchase.consult（查询买断或时长访问决策）](api-list/alipay_aipay_nowpay_purchase_consult.md)，业务入参示例：

```json
{
  "out_product_id": "app_writing_001",
  "external_owner_id": "creator_001",
  "external_buyer_id": "user_001",
  "callback_url": "https://platform.example.com/nowpay/purchase-return"
}
```

| decision | 平台操作 |
| --- | --- |
| `ALLOW` | 放行。时长包按返回的 `valid_from`、`valid_until` 展示有效期 |
| `PURCHASE_REQUIRED` | 使用返回的 `purchase_url` 或 `purchase_qr_code` 引导购买 |
| `DENY` | 不放行、不新建购买入口；根据 `reason_code` 展示说明或刷新 |

时长包权益区间为 `[valid_from, valid_until)`，在结束时间点失效。有效权益存在时，不引导用户重复购买。购买返回后仍需重新查询，只有新的 `decision=ALLOW` 才开放服务。

若支付页面返回后权益暂未可用，可进行有限次查询并提示稍后刷新。不要因暂未查到权益而直接认定支付失败、自动再次支付或重复开放服务。

### 次数包和积分包

```mermaid
sequenceDiagram
    autonumber
    participant U as 用户
    participant P as 平台
    participant N as 即刻收 OpenAPI
    participant H as 支付宝托管购买页
    P->>N: alipay.aipay.nowpay.quota.query
    N-->>P: quota_unit / total / used / remaining
    P->>P: 按服务规则计算所需额度
    opt 额度不足或用户主动加购
        P->>N: alipay.aipay.nowpay.purchase.create
        N-->>P: purchase_url / expire_time
        U->>H: 确认购买并支付
        H-->>P: 返回 callback_url
        P->>N: alipay.aipay.nowpay.quota.query
        N-->>P: 最新余额
    end
    P->>P: 持久化消费请求号及业务参数
    Note over P,N: 平台按约定的服务交付时点发起正式核销
    P->>N: alipay.aipay.nowpay.quota.verify
    N-->>P: 核销状态或业务错误
    opt 处理中、超时或结果未知
        P->>N: alipay.aipay.nowpay.quota.refresh（原请求号）
        N-->>P: 核销结果
    end
    P->>P: 按最终结果更新消费和服务记录
```

1. 调用 [alipay.aipay.nowpay.quota.query（查询次数或积分余额）](api-list/alipay_aipay_nowpay_quota_query.md)，展示用户的可用余额。未购买时返回零余额。
2. 平台按具体服务规则计算所需额度，例如生成一篇文章消耗 1 次，处理一次复杂任务消耗 10 积分。
3. 额度不足或用户主动加购时，调用 [alipay.aipay.nowpay.purchase.create（获取购买链接）](api-list/alipay_aipay_nowpay_purchase_create.md)。可传入查询得到的 `sku_id` 锁定档位，也可省略，让用户在购买页选择。
4. 用户返回后调用 `alipay.aipay.nowpay.quota.query` 刷新余额。未到账时有限次刷新或提示稍后查询。
5. 在平台确定的服务交付时点，调用 [alipay.aipay.nowpay.quota.verify（核销次数或积分）](api-list/alipay_aipay_nowpay_quota_verify.md)。前置余额充足仍需正式核销，不能仅按余额查询结果执行本地扣减。
6. 对处理中或未知结果，使用原 `out_request_no` 调用 [alipay.aipay.nowpay.quota.refresh（查询核销结果）](api-list/alipay_aipay_nowpay_quota_refresh.md)，或用完全相同的原参数重试核销。

指定档位购买的 `biz_content` 示例：

```json
{
  "out_request_no": "purchase_20260907_000001",
  "out_product_id": "app_writing_001",
  "external_owner_id": "creator_001",
  "external_buyer_id": "user_001",
  "sku_id": "S0806000200863003",
  "callback_url": "https://platform.example.com/nowpay/purchase-return"
}
```

`sku_id` 不指定时打开普通购买页。平台不传价格或价格版本参与创单；即刻收在用户确认购买时重新校验商品和档位。购买链接与二维码按不透明入口使用，不解析令牌，不自行拼接。

### 额度核销与恢复示例

以下两组参数对应同一笔消费，查询必须使用核销时的原请求号。次数核销也必须显式传入 `amount=1`。

::::aipay-tabs{defaultActiveKey="核销额度"}
:::aipay-tab{key="核销额度" title="核销额度"}
```json
{
  "out_request_no": "consume_20260907_000001",
  "out_product_id": "app_writing_001",
  "external_owner_id": "creator_001",
  "external_buyer_id": "user_001",
  "amount": 1,
  "consume_reason": "生成一篇文章"
}
```
:::

:::aipay-tab{key="查询原核销结果" title="查询原核销结果"}
```json
{
  "out_request_no": "consume_20260907_000001",
  "out_product_id": "app_writing_001",
  "external_owner_id": "creator_001",
  "external_buyer_id": "user_001"
}
```
:::

::::

`consume_reason` 使用最长 256 字符的业务说明，平台自行持久化。不要填写完整提示词、用户隐私、业务 JSON 等内容，也不要依赖查询结果回传该字段恢复原业务上下文。

| 核销结果 | 是否确认扣减 | 平台处理 |
| --- | --- | --- |
| `code=10000` 且 `consume_status=SUCCEEDED` | 是 | 保存核销流水、实扣量及结果，按业务约定完成服务记录 |
| `code=10000` 且 `consume_status=FAILED` | 否 | 按原因处理；余额不足引导补充额度 |
| `code=10000` 且 `consume_status=PROCESSING` | 待确认 | 使用原请求号查询，避免并发重扣 |
| `NOW_PAY_QUOTA_INSUFFICIENT` | 本次请求未确认成功 | 处理余额不足，不将网关失败忽略为正常成功 |
| 网络超时、系统错误或未知状态 | 待确认 | 保存原请求，查询或原参数重试 |
| 核销记录不存在 | 待确认 | 核对请求号与商品，继续查询或原参数重试；不换号重扣 |

平台应同时处理业务错误码和成功响应中的核销状态。`remaining` 仅在成功扣减时用作该笔扣减后的余额；结果查询返回的是原核销结果，需要实时余额时调用 `alipay.aipay.nowpay.quota.query`。

核销与平台自身服务交付是两个动作。平台须根据业务明确先核销还是先交付，并对服务执行、超时恢复、交付失败处理做一致设计。当前能力不提供核销成功后的自动返还，不应将核销当作可自动释放的预占。

## 第三步：启停新增购买

调用 [alipay.aipay.nowpay.charge.modify（启停收费能力）](api-list/alipay_aipay_nowpay_charge_modify.md)：

```json
{
  "out_product_id": "app_writing_001",
  "external_owner_id": "creator_001",
  "action": "DISABLE"
}
```

`DISABLE` 停止新增购买，`ENABLE` 恢复新增购买。成功后按 `capability_status` 刷新页面；`changed=false` 表示已处于目标状态。若操作超时，先查询当前状态，再决定是否重试原动作。

停用后原有买断、时长或额度权益仍按对应接口结果处理。此接口不变更价格，也不退款或回收已有权益。

# 请求与响应处理

## 服务端调用

业务参数序列化为 JSON 后放入 `biz_content`，与 `app_id`、`method`、`charset`、`sign_type`、`timestamp`、`version` 等公共参数一起签名提交。每份 API 文档均提供 Java 和 cURL 示例，参见 [API 列表](api-list.md)。

所有接口返回 JSON 业务结果，再由平台打开结果里的页面链接。接口调用使用服务端 SDK 的普通执行方法，如 Java 的 `execute`。不要将这些接口作为直接输出 HTML 支付表单的页面支付接口使用。

以额度查询为例，响应封装如下：

```json
{
  "alipay_aipay_nowpay_quota_query_response": {
    "code": "10000",
    "msg": "Success",
    "quota_unit": "COUNT",
    "total": 20,
    "used": 0,
    "remaining": 20,
    "as_of_time": "2026-09-07 10:00:00"
  },
  "sign": "RESPONSE_SIGNATURE_PLACEHOLDER"
}
```

上例仅说明响应结构，签名不是有效签名。平台先验签、再判断 `code`；`code=10000` 只说明接口调用成功，业务是否允许访问或扣减是否成功，还需读取对应的业务状态。

## 幂等与重试

| 操作 | 平台应保存的定位信息 | 重试原则 |
| --- | --- | --- |
| alipay.aipay.nowpay.charge.initialize | 商品、创作者和首次初始化参数 | 相同商品复用配置申请；结果未知时原参数重试，已配置则查询管理入口 |
| alipay.aipay.nowpay.charge.modify | 商品、创作者和目标 action | 先查状态；必要时重试原动作 |
| alipay.aipay.nowpay.purchase.create | 独立购买入口请求号及完整业务参数 | 有效期内同请求复用入口；超时不换号。确认链接失效后，新购买入口使用新号 |
| alipay.aipay.nowpay.quota.verify | 消费请求号、商品、受益人、amount、consume_reason | 使用原请求号和原参数重试，或查询原核销结果 |
| alipay.aipay.nowpay.quota.refresh | 原消费请求的定位信息 | 只查询原核销记录，不生成新的核销号 |

平台应保证 `out_request_no` 在其业务范围内唯一，不跨商品、用户或不同消费复用。购买链接幂等具有时效，不可用作长期订单查重。不要把购买链接请求号当成支付宝交易号，也不要用购买接口重新生成入口来恢复核销结果。

对可恢复异常采用有限次数、带间隔的查询或重试；超过平台预设等待时间后保留“待确认”状态，由后续查询或排查恢复。不要因达到等待上限就将未知结果强制判为失败。

## 页面返回与通知

`callback_url` 仅用于用户或创作者操作结束后的页面跳转。买断与时长包在返回后查询 `alipay.aipay.nowpay.purchase.consult`，额度包查询 `alipay.aipay.nowpay.quota.query`，收费配置查询 `alipay.aipay.nowpay.charge.query`。

## 错误处理

1. 网关或签名错误：按[支付宝公共错误码](https://opendoc.alipay.com/common/02km9f)排查公共参数、应用权限和验签配置。
2. 参数、商品或模式错误：按具体 API 的 `sub_code` 核对业务参数及商品配置；不依赖 `sub_msg` 的展示文案编写业务分支。
3. 核销余额不足：兼容 `NOW_PAY_QUOTA_INSUFFICIENT` 业务错误及 `FAILED` 的结果表达，不确认消费成功。
4. 幂等冲突：读取平台已保存的原请求进行核对；不能通过替换请求号掩盖一笔未确认的消费。
5. 核销未找到记录或依赖异常：保留原请求号，继续查询或原参数重试。公开预览与当前服务端部分错误码命名存在差异，按核销 API 的“联调兼容处理”覆盖。