保险产品App接入支付宝实名合单支付能力咨询
结论
支付宝 App 支付可供已实名用户付款,但 App 支付、身份核验与合单支付是三项不同的能力。支付成功本身不能证明付款人的身份符合保险业务要求。
保险产品可按以下流程接入:
- 支付前,通过支付宝身份认证能力核验投保人或付款人。
- 服务端校验认证结果,确认其与保险业务中的姓名、证件信息一致。
- 认证通过后,调用
alipay.trade.app.pay创建支付订单。 - 如果多张保单需要一次付款,可由商户在业务系统内合并金额,生成一个支付宝交易订单,并保留内部保单明细。
支付宝是否向特定保险商户提供独立的“实名合单支付”能力,取决于商户签约产品、行业准入要求和开放平台当前的接口文档。在获得明确权限前,不能认为 App 支付接口原生支持将多个独立支付宝交易订单合并付款,并对每个订单分别进行实名校验。
为什么不能只检查支付结果
alipay.trade.app.pay 主要用于创建 App 支付交易。支付成功通常只能说明交易已经完成,无法直接证明:
- 付款人的实名信息与投保人一致;
- 付款人的证件号码符合保险业务要求;
- 每张保单都完成了实名校验;
- 商户提交的姓名和证件号码已经过支付宝核验。
buyer_id、登录账号、手机号及支付结果中的用户标识,也不能代替实名身份认证。这些信息可以用于关联支付宝用户,但不能作为保险业务所需的姓名、证件号码一致性证明。
推荐接入流程
1. 确认产品权限
开发前,需要向支付宝服务商或行业运营确认:
- 当前商户能否接入 App 支付;
- 是否已经取得支付宝身份认证相关产品的权限;
- 保险场景是否允许他人代付;
- 是否有面向保险行业的实名支付或合单支付专用能力;
- 可以保存认证结果中的哪些字段,以及允许保存多长时间;
- 合单后的退款、撤销和对账应按支付单还是保单处理。
相关规则可能因商户类型、签约主体和支付宝产品政策而变化,应以实际签约结果及开放平台控制台显示的能力为准。
2. 先完成身份认证
客户端发起认证前,服务端应先创建认证业务记录。认证结束后,必须由服务端查询或接收认证结果,不能采信客户端自行提交的“认证成功”状态。
服务端至少应保存:
- 商户侧认证流水号;
- 业务用户编号;
- 支付宝认证流程标识;
- 认证状态;
- 认证完成时间;
- 认证信息与投保信息的匹配结果。
姓名和证件号码属于敏感个人信息,不应写入日志、支付 body、回传参数或客户端可篡改的字段。
3. 认证通过后创建支付订单
以下示例说明服务端的控制逻辑。身份认证接口的名称和结果字段,需要根据商户实际获批的支付宝认证产品进行替换。示例中的 identityService 不是支付宝官方 API。
public String createInsuranceAppPay(PayRequest input) throws Exception {
IdentityResult identity = identityService.query(input.getCertificationId());
if (!identity.isPassed()) {
throw new IllegalStateException("付款人尚未完成实名认证");
}
if (!identity.belongsTo(input.getBusinessUserId())) {
throw new IllegalStateException("认证结果与当前业务用户不匹配");
}
if (!insuranceOrderService.canPay(input.getOutTradeNo())) {
throw new IllegalStateException("保险订单状态不允许支付");
}
AlipayTradeAppPayModel model = new AlipayTradeAppPayModel();
model.setProductCode("QUICK_MSECURITY_PAY");
model.setOutTradeNo(input.getOutTradeNo());
model.setSubject("保险订单支付");
model.setTotalAmount(input.getTotalAmount().toPlainString());
model.setTimeoutExpress("15m");
AlipayTradeAppPayRequest request = new AlipayTradeAppPayRequest();
request.setBizModel(model);
request.setNotifyUrl("https://example.com/alipay/payment/notify");
AlipayTradeAppPayResponse response =
alipayClient.sdkExecute(request);
if (!response.isSuccess()) {
throw new IllegalStateException(
"创建支付宝订单失败:" + response.getSubCode()
);
}
return response.getBody();
}
客户端只需使用服务端返回的订单字符串唤起支付宝:
PayTask payTask = new PayTask(activity);
Map<String, String> result = payTask.payV2(orderInfo, true);
客户端返回的结果只用于页面展示。最终支付状态应以支付宝异步通知的验签结果,或服务端主动查询的结果为准。
多张保单一次付款的处理方式
如果商户没有开通支付宝侧的实名合单产品,可以在内部建立支付主单与保单子单的关联关系:
{
"paymentOrderNo": "PAY202609090001",
"payerCertificationId": "CERT_xxx",
"totalAmount": "300.00",
"policyOrders": [
{
"policyOrderNo": "POLICY001",
"amount": "100.00"
},
{
"policyOrderNo": "POLICY002",
"amount": "200.00"
}
]
}
服务端创建支付宝订单前,应校验:
totalAmount = Σ policyOrders[i].amount
还要确认所有子单遵守相同的付款约束,包括:
- 对应同一个已认证付款人;
- 币种一致;
- 商户主体一致;
- 均处于待支付状态;
- 没有超过各自的支付有效期;
- 符合保险业务对投保人、被保险人和付款人的限制。
支付宝支付成功后,由商户系统把支付主单金额分配到各张保单。此时,一个支付宝交易对应多个内部业务订单,但这不等同于支付宝原生的多交易合单支付。
退款与对账注意事项
商户在内部合单后,退款通常仍基于同一个支付宝交易号处理。如果只退部分保单,商户需要自行计算退款金额并记录各子单的退款明细,所有退款的累计金额不得超过原支付金额。
接入时还需注意:
out_trade_no必须全局唯一;- 金额应使用十进制定点数,避免使用
double计算; - 收到异步通知后,必须验签,并校验
app_id、商户身份、订单号和金额; - 通知可能重复到达,业务处理必须保证幂等;
- 不要将姓名、身份证号等敏感信息放入
subject、body或passback_params; - 支付前的身份认证不能代替支付后的订单状态确认;
- 如果保险规则不允许代付,应在身份认证、业务订单与实际付款账号之间建立可验证的绑定关系。
较稳妥的接入顺序是先完成实名核验,再进行 App 支付,合单关系则由业务系统管理。只有支付宝明确为该保险商户开通实名合单产品,并提供相应的接口和字段说明后,才应改用支付宝侧的原生合单方案。
备注:内容仅供参考。
