最近在接iOS 的支付功能,碰到一些问题,简单罗列一下:
1,支付刷单的问题。刷单在android和iOS上都存在,而且,如果你不做处理,刷单问题就会非常严重。对于一些商品类的应用,可能会造成比较大的损失。
1,每一笔订单完成后,会生成一个receipt,就是一个交易的凭证,这个交易的凭证,需要上传到服务端,由服务端和iOS 的服务器进行验证。
2,有时候服务端能验证成功,但是这比订单也有可能是刷的,原因是hack修改了这个凭证,所以需要验证这个凭证的订单号。因为对于支付来说,订单号是唯一的,所以对于同一个订单号,可能被人为的修改成了多笔订单。服务端对每笔订单的订单号要做个记录,每次验证订单后,从订单号中查找是否有相同的订单号,如果有,那这笔订单就可能有问题。
3,receipt实际上是交易成功后storekit保存到沙盒里面的一个数据,这个数据可能是多笔订单生成的。所以对于一些漏单的情况,只要这个receipt生成了,如果这个时候断网或者关机,第二次启动的时候,应该向服务端验证下之前漏单的可能性。
4,今天调试一个手机时,购买一个产品,弹窗
其它手机没这个问题,而且,换其它商品也没出现问题。
google了一下,大概明白了原因,是因为之前的交易异常终止了,没有调用finishTransaction接口,造成再去购买这个产品的时候,发现你的paymentqueen里面还有这个商品的交易未完成,所以提示说你已购买过这个商品,正在为您免费恢复。
但是我把所有的delegate打开,发现点击了这个弹窗的ok键后,没有任何回调给客户端,所以就没办法在payment自动检测到这种场景后,再处理了。
因此需要一进入支付的场景,就自动检测下queen里面是否有处理完的订单但是没有fininsh的。如果有,强制finish掉。至于是否要跟自己的服务器执行相关的支付动作,看具体的业务逻辑。
核心代码如下
let transactions = SKPaymentQueue.default().transactions
if transactions.count > 0{
for i in 0..<transactions.count{
let trans = transactions[i]
if trans.transactionState == .purchased{
SKPaymentQueue.default().finishTransaction(trans)
}
}
}