PAYATHON 2026

total_payments 设为 3 后是否会自动解约?

支付小周

结论

不能把 total_payments=3 理解为成功扣款 3 次后协议一定会自动解约。

该参数表示商户最多可以依据这份协议成功扣款 3 次。达到上限后,商户不能再继续成功扣款,但这不等于协议状态会自动变为已解约。仅从 total_payments 的参数说明,无法判断支付宝是否会自动执行解约。

如果业务规定协议必须在第三次扣款成功后终止,商户应主动查询协议状态,并按照当前开放平台文档调用解约接口,不能根据扣款次数推断协议已经解约。

原因

total_payments 限制的是成功扣款次数。例如:

total_payments = 3

其含义通常是:

  • 第 1 次成功扣款后,累计成功 1 次;
  • 第 2 次成功扣款后,累计成功 2 次;
  • 第 3 次成功扣款后,达到次数上限;
  • 此后不能再依据该协议成功扣款。

参数说明只限定了成功扣款次数,没有明确说明达到上限后会同步修改协议状态,也没有说明系统会自动发送解约通知。因此,业务系统需要分别记录以下两个状态:

扣款额度是否已经用完
协议是否已经解约

协议仍然存在但不能继续扣款,与协议已经正式解约,是两种不同的状态。

建议的处理方式

1. 签约时保存协议标识

通过 alipay.user.agreement.page.sign 完成签约后,保存支付宝返回的协议号和签约状态。后续查询、扣款及解约都应使用真实的协议标识,不能只根据本地扣款次数关联协议。

签约参数示意:

{
  "product_code": "实际产品码",
  "personal_product_code": "实际个人产品码",
  "sign_scene": "实际签约场景",
  "total_payments": 3
}

具体必填字段以商户当前所用产品的开放平台文档为准。

2. 只统计最终成功的扣款

商户应结合支付宝返回结果和异步通知确认扣款是否成功,不能在请求发出后就增加成功次数。

伪代码示例:

PaymentResult result = executePayment(agreementNo);

if (result.isSuccess()) {
    int successCount = paymentRepository.countSuccessfulPayments(agreementNo);

    if (successCount >= 3) {
        agreementRepository.markPaymentLimitReached(agreementNo);
        stopCreatingNewPaymentRequests(agreementNo);
    }
}

实际系统还应根据支付宝交易号或商户订单号进行幂等处理,防止重复通知造成重复计数。

3. 查询真实协议状态

成功扣款达到 3 次后,通过支付宝提供的协议查询能力核实协议状态。如果当前产品支持 alipay.user.agreement.query,可以使用协议号查询。具体请求字段和状态枚举以当前接口文档为准。

逻辑示意:

AgreementStatus status = queryAgreementStatus(agreementNo);

if (status.isEffective()) {
    // 协议可能仍有效,但扣款次数已经达到上限
    stopCreatingNewPaymentRequests(agreementNo);
} else if (status.isTerminated()) {
    agreementRepository.markTerminated(agreementNo);
}

不要因为本地记录的 successCount == 3,就直接将支付宝侧的协议状态标记为已解约。

4. 业务需要明确终止时主动解约

如果业务规则要求第三次成功扣款后立即终止协议,应在确认该笔扣款成功后,调用适用于当前产品的解约接口。部分签约产品使用 alipay.user.agreement.unsign,但该接口是否适用以及需要传入哪些参数,仍应以对应产品和当前版本的接口文档为准。

处理流程可以设计为:

收到扣款成功通知
        ↓
进行订单幂等校验
        ↓
统计该协议的成功扣款次数
        ↓
次数达到 3
        ↓
停止发起后续扣款
        ↓
查询支付宝侧协议状态
        ↓
如协议仍有效且业务要求终止,则调用解约接口
        ↓
根据解约结果或通知更新本地状态

注意事项

  • total_payments 限制的是成功扣款次数,不是扣款请求次数。失败、处理中或关闭的交易不能直接计入成功次数。
  • 第三次扣款成功后是否会自动改变协议状态,应以该签约产品的最新接口文档和实际返回状态为准,不能仅根据参数名称判断。
  • 如果参数说明没有明确退款后是否恢复可扣款次数,不要自行假设。可以向支付宝技术支持确认,或在沙箱及测试商户环境中验证。
  • 扣款通知可能重复送达,本地计数必须进行幂等处理。
  • 即使支付宝侧会阻止超过上限的扣款,商户也应在本地停止生成新的扣款请求,以免产生无效请求和异常告警。
  • 解约是独立的业务动作。如果必须确保协议终止,应检查解约接口的响应及后续协议状态,不能只记录已发起解约。

备注:内容仅供参考。