php服务端处理 ios内购充值

 其他知识   高蒙   阅读(186)   评论(2)   2018-12-24 10:31:14    app ios内购 php 


app一直没有接入iOS内购充值,随着业务支付功能越来越多,ios内购充值就提到日程上来了。那么,ios内购充值怎么做呢?

其实iOS内购充值是通过客户端接入iOS的IAP模块(In-AppPurchase)后,由客户端发起充值,然后再把充值数据(receipt)发给服务端,最后由服务端远程调用AppStore服务器验证。

具体的流程如图:

111.png


服务端连接AppStore验单

验单的过程是,服务端发起HTTP Post请求,将以下字段的数据以json格式请求 AppStore 服务器,解析返回数据来验证。

字段:receipt-data

来源:ios端内置的生成base64编码的token。


AppStore 服务器有两个,对应测试环境(沙盒测试)和正式环境:

测试环境: https://sandbox.itunes.apple.com/verifyReceipt

正式环境: https://buy.itunes.apple.com/verifyReceipt


// $verification_uri = 'https://buy.itunes.apple.com/verifyReceipt';
$verification_uri = 'https://sandbox.itunes.apple.com/verifyReceipt';
 
$post_data = array(
    'receipt-data'=>$receipt_data // 此处的值 是ios客户端生成的验签token
);
$ch = curl_init($verification_uri);
curl_setopt($ch, CURLOPT_RETURNTRANSFER, true);
curl_setopt($ch, CURLOPT_POST, true);
curl_setopt($ch, CURLOPT_POSTFIELDS, json_encode($post_data));
 
$response = curl_exec($ch);
$errno    = curl_errno($ch);
$errmsg   = curl_error($ch);
curl_close($ch);
 
if ($errno != 0) {
throw new Exception($errmsg, $errno);
}
$data = json_decode($response, 1);



服务端验证返回数据

iOS发起票据验证请求后,通过处理AppStore返回数据来验单。下面举两个示例,同时说明不同iOS版本的返回数据不同,服务端要做好区别。

1、iOS7及以上获取的票据返回数据:

{
receipt =  {
        "adam_id" = 0,
        "app_item_id" = 0,
        "application_version" = 1,
        "bundle_id" = "com.test",
        "download_id" = 0,
        "in_app" = {
{
    "is_trial_period" = false,
    "original_purchase_date" = "2017-01-01 01:01:01 Etc/GMT",
    "original_purchase_date_ms" = 1483203661000,
    "original_purchase_date_pst" = "2017-01-01 01:01:01 America/Los_Angeles",
    "original_transaction_id" = 1000000000000001,
    "product_id" = "com.test.10",
    "purchase_date" = "2017-01-01 01:01:01 Etc/GMT",
    "purchase_date_ms" = 1483203661000,
    "purchase_date_pst" = "2017-01-01 01:01:01 America/Los_Angeles",
    "transaction_id" = 1000000000000001
},
//......
},
        "receipt_type" = ProductionSandbox,
        "request_date" = "2017-01-01 01:01:01 Etc/GMT",
        "request_date_ms" = 1483203661000,
        "request_date_pst" = "2017-01-01 01:01:01 America/Los_Angeles",
        "version_external_identifier" = 0,
    },
    status = 0
}

2、iOS7以下获取的票据返回数据(不包括iOS7):

{
    receipt = {
        "bid" = "com.test",
        "bvrs" = 1,
        "item_id" = 573837050,
        "original_purchase_date" = "2017-01-01 01:01:01 Etc/GMT",
        "original_purchase_date_ms" = 1483203661000,
        "original_purchase_date_pst" = "2017-01-01 01:01:01 America/Los_Angeles",
        "original_transaction_id" = 1000000000000001,
        "product_id" = "com.test.10",
        "purchase_date" = "2017-01-01 01:01:01 Etc/GMT",
        "purchase_date_ms" = 1483203661000,
        "purchase_date_pst" = "2017-01-01 01:01:01 America/Los_Angeles",
        "transaction_id" = 1000000000000001
    },
    status = 0
}


验证订单是否成功,关键看这几个数据:

1、status为 0 表示成功;其他都为失败,表示失败原因

2、根据 receipt.in_app 字段判断iOS版本,验证方法也不同

iOS7及以上:有in_app字段,验证 receipt.bundle_id 是否为你 App 的 bundle id,根据 in_app 处理充值的每一笔订单, 根据 product_id 判断用户充值了哪个档位,同时取出 transaction_id

iOS7以下:没有in_app字段,验证 receipt.bid 是否为你 App 的 bundle id,根据 product_id 判断用户充值了哪个档位,同时取出 transaction_id

3、根据 transaction_id 对比数据库历史订单判断是否已处理过,没有则认为本次充值是有效的。


iOS充值坑点: in_app 究竟是什么

receipt.in_app 是请求AppStore验单后返回的数据,前面有提及,为用户的充值订单数据。


有两个问题要注意:

1、iOS内购充值时,客户端充值后从iOS得到的票据 receipt_data 不是针对本次充值的,而是相当于给一个授权 token, 获取用户 appleid 账号在本 App 中所有未关闭的充值记录,包括刚刚发起的充值。

2、根据这个票据查到的充值数据(receipt.in_app) ,除了最近发起的充值,还包括了非消耗品型,订阅型的充值数据。其中,最近发起的充值,不只是刚刚发起的充值,还可能是最近的几笔充值。特别是沙盒测试,还可能拿到已经确认关闭了的充值订单


所以,取到充值数据,不是取 receipt.in_app 中的第一个数据、或最后一个,而是在客户端完成充值后,将AppStore回调给到的 transaction_id 拿来做匹配。


iOS充值坑点:App审核不通过

苹果审核App时,是在沙盒环境下测试。所以,当App提交苹果审核时,服务端需换成沙盒环境,否则就无法通过苹果审核。通常游戏开发商都会搞一个审核服来给苹果审核,这样,审核服用沙盒环境,正式服用正式环境。


但对于很多App应用开发商来说,专门搞一个服务器显然增加了不少成本。其实还是有办法处理的,方法如下:

根据验单返回的 status 字段:

222.png

当 status = 21007 时,把请求地址换成沙盒测试地址,再次请求验单。





相关文章



我要评论


站长昵称:(*)

输入内容:


评论列表


高蒙

男,程序猿一枚

 

人生要是没有理想, 那跟一条咸鱼有什么分别。


关于我

  http://www.shuchengxian.com

高蒙个人博客是以PHP技术为主的程序员个人博客。博客主要发布php开发中遇到的问题以及解决办法,同时个人博客也分享网站模板素材,jquery插件等方面素材。


站点声明:相关侵权、举报、投诉及建议等,请发E-mail:936594075#qq.com(#替换成@)。

Copyright © 2018, www.shuchengxian.com, All rights reserved. 个人博客皖公网安备 34152302000022号 皖ICP备15015490号

关键词:个人博客,PHP博客,PHP博客程序,高蒙博客,高蒙个人博客,php程序员博客,程序员个人博客