支付宝信用免押踩坑指南

背景

信用免押

近期对接支付宝的信用免押功能,发现跟微信支付类似,这些个大厂的对接文档质量跟错误提示实在是、一言难尽……

总结一下过程中一些比较典型的问题,就当是做个记录吧。

过程

因为曾经对接过支付宝的h5支付,所以服务端大部分可以重用,不过这里也是埋了坑,下面会提到。

另附一个支付宝的错误码查询页面

系统繁忙,请稍后再试(ALIN1018031)

客户端报错

首次在客户端拉起支付的时候就遇到了这个报错,从客户端的回调来看,只有一个“6001 支付未完成”的信息,可以说没有任何帮助。

  • 根据官方指南检查产品签约状态,并未发现异常;
  • 因为曾经对接过h5支付,所以签名也不会有什么问题;
  • 精简参数,只留必填数据,报错依旧;
  • 替换参数中的中文,终于,错误信息发生了变化……

这里就是第一个坑

信用免押支付必须使用utf-8的形式来传递中文,否则就会报错。

对应的代码也就是

1
2
3
4
5
6
7
private AlipayClient alipayClient = new DefaultAlipayClient(
alipayGateway
, alipayAppid
, alipayPrivateKey
, "json", "UTF-8"
, alipayPlatformPublicKey
, "RSA2");

然后就是第二个坑

在使用UTF-8编码的情况下又会导致h5支付不正常

所以正确的做法是,初始化2个AlipayClient对象实例,然后根据场景选用。

订单参数异常,请重新下单后再发起付款。(ALIN42682)

前面中文的坑摊过去之后有提到错误提示变了,就是变成了这个ALIN42682

支付宝分明知道参数有错,但是不会告诉你是哪里的错,这就是大厂错误提示可恨的地方。

仔细核对文档后发现了几个比较容易出错的地方:

  • 请求流水号参数(out_request_no)只能包含中文、英文、数字,这里往往不自觉的就会带入一个“-”符号;
  • 收款方的支付宝唯一用户号(payee_user_id)对应的是商家的,也就是自己的用户号,可以根据官方指引进行查询,这里一不小心就会用成了客户的;
  • 信用服务Id(serviceId)接口文档中说的是“信用场景下必传,具体值需要联系芝麻客服。”,可以根据这个文档的指引获取;
  • 如果说想使用全渠道支付,也就是银行卡、信用卡、花呗、余额宝等,可以不用指定支付渠道(enable_pay_channels),因为在官方接口文档上只给出了余额宝(MONEY_FUND)、花呗(PCREDIT_PAY)以及芝麻信用(CREDITZHIMA)这三种的枚举值;
  • 请求流水号(out_request_no)不需要像接口文档中说的每次不一样,如果是这样的话就会造成第一次支付如果取消了,后续就无法再拉起支付的问题,通常来说使用自己的订单号、然后配合最晚付款时间(pay_timeout)来控制就行了。

资金授权解冻出现“系统繁忙(isp.unknow-error)”

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
{
"amount": "",
"authNo": "",
"body": "{\"alipay_fund_auth_order_unfreeze_response\":{\"code\":\"20000\",\"msg\":\"Service Currently Unavailable\",\"sub_code\":\"isp.unknow-error\",\"sub_msg\":\"系统繁忙\"},\"sign\":\"...\"}",
"code": "20000",
"creditAmount": "",
"errorCode": "20000",
"fundAmount": "",
"gmtTrans": null,
"msg": "Service Currently Unavailable",
"operationId": "",
"outOrderNo": "",
"outRequestNo": "",
"params": {
"biz_content": "{\"amount\":\"0.01\",\"auth_no\":\"...\",\"extra_param\":\"{\\\"unfreezeBizInfo\\\":{\\\"bizComplete\\\":\\\"true\\\"}}\",\"out_request_no\":\"...\",\"remark\":\"押金预授权解冻\"}"
},
"status": "",
"subCode": "isp.unknow-error",
"subMsg": "系统繁忙",
"success": false
}

虽然接口调用出错了,单实际上资金解冻是成功的,并且立刻就收到了回调通知,所以这里无视调这个错误,以回调通知的结果为准就好了。