谷歌Google Play内购支付后端指南

2023-12-05 :谷歌内购相关流程今时不同往日,本文大部分内容对比实际情况已经产生偏离,请谨慎参考!

2021-08-19 10:22 更新今天公司项目进行迁移了,所以更新几张图片,整理流程没有变化

2021-05-18 16:06 更新最近好多人来问怎么对接谷歌的接口。如果贵项目服务器是在海外,我建议是直接使用谷歌的SDK。如果跟我一样,项目服务器在国内,需要代理,那么就必须自己编写请求。我把我的代码整理了出来,供大家参考,方便快速入手谷歌API对接,希望可以对您有所帮助。

https://github.com/Lichmaker/google-api-demo/blob/main/GoogleIAPService.php

文章内有一些图片,因为谷歌的更新,UI有变化,所以看起来会不一样。但是流程大致上没什么变化。

前言前段时间在公司负责与Android对接了Google Play支付,国内大部分的文章都是介绍前端(APP)的对接,后端的处理讲解少之又少,所以决定整理出来。

本篇只会介绍Google Play中一次性商品的对接,订阅类商品没有接触过,但是差别应该只在最后的订阅扣费(看了一下文档瞎猜的),前面大部分应该都是两者共同需要的。

如果你的业务机器是海外服务器,可以直接连通谷歌的服务,那么我建议你简单阅读本篇,了解大概流程之后直接上谷歌提供的SDK,非常的方便。

如果你跟我一样,是国内的服务器,但是不得不使用谷歌服务,可以跟我一样全程自己撸码,然后使用 代理转发 等技术在另一台海外机器中做代理。

账号配置与 Google Play 绑定首先,要触发 Google API Console 和 Google Play Console 触发绑定。

我尝试了2个账号,发现绑定的唯一方法,是在 Google Play Console 中触发生成 OAuth 凭证,此时会跳转到 Google API Console 中,若当前项目的名称,变成有 Google Play 字样,则为绑定成功。

注: 后续的操作,务必要在 Google Play 的项目中完成,否则调用 API 的时候会提示未于 Google Play 进行绑定

启用 API点击 "库" 或者 "+启用API和服务" , 搜索 androidpublisher , 点击进去并进行启用

生成后端使用的凭证网域验证这个没什么好说的,根据谷歌的指引走,配置一下 DNS ,一下子就可以弄好

OAuth 同意屏幕设置这里设置主要需要注意配置好 已授权网域,用于 OAuth 中设置 callback url

创建新的 OAuth 凭证选择 “Web 应用” 进行 OAuth 凭证创建,设置好重定向URI并且为刚才设置的 已授权网域 下的URI

获取 refresh tokenrefresh token 很关键,是用于后端生成 access_token 的唯一凭证,生成之后必须妥善保管。

参考文档: https://developers.google.com/android-publisher/authorization#generating_a_refresh_token

首先,构建url,直接在浏览器访问,然后登陆Google账号并授权允许。 之后就会携带参数跳转到指定的重定向URI

https://accounts.google.com/o/oauth2/auth?client_id={你的OAuth client id}&scope={授权范围}&response_type=code&redirect_uri={重定向URI}&access_type=offline注意,access_type=offline 是必须的,如果不带这个,将不会生成出 refresh_token。 内购需要的授权范围为 https://www.googleapis.com/auth/androidpublisher ,如果你有其他的业务需要授权(如推送相关的 Firebase 服务,则需要使用英文空格进行分隔)。 完整例子如下:

https://accounts.google.com/o/oauth2/auth?client_id=我的CLIENT不给你看&scope=https://www.googleapis.com/auth/firebase.messaging&response_type=code&redirect_uri=http://mywebsite.com/myuri&access_type=offline授权完成后,谷歌会携带参数跳转到你的重定向URI中。其中包含了最重要 code 字段,拿这个 code 去进行下一步操作,获取 refresh_token

HTTP POST

URL:

https://accounts.google.com/o/oauth2/token

POST BODY:

code:刚才拿到的code值

client_id:OAuth 凭证中的 client_id

client_secret:OAuth 凭证中的 client_secret

redirect_uri:跟上一个url构建中的重定向uri一致

grant_type:authorization_code

请求完成后,会返回 json respond ,例:

{

"access_token" : "ya29.ZStBkRnGyZ2mUYOLgls7QVBxOg82XhBCFo8UIT5gM",

"token_type" : "Bearer",

"expires_in" : 3600,

"refresh_token" : "1/zaaHNytlC3SEBX7F2cfrHcqJEa3KoAHYeXES6nmho"

}请务必妥善保管好 refresh_token ,以免泄漏。

获取 access_token使用上一步获取到的 refresh_token ,通过 HTTP POST 获取 access_token

HTTP POST

URL:

https://accounts.google.com/o/oauth2/token

POST BODY:

grant_type:refresh_token

client_id:OAuth 凭证中的 client_id

client_secret:OAuth 凭证中的 client_secret

refresh_token:上一步拿到的 refresh_token请求成功后,在 json respond 中可以拿到 access_token,且有过期时间。

{

"access_token" : "ya29.AHES3ZQ_MbZCwac9TBWIbjW5ilJkXvLTeSl530Na2",

"token_type" : "Bearer",

"expires_in" : 3600,

}支付流程获取用户支付订单信息接口文档: https://developers.google.com/android-publisher/api-ref/purchases/products/get

当用户在 APP 中完成支付后,前端可以从谷歌手上拿到一个 token ,该 token 上报给后端服务可以用来查询订单状态,并进行订单消费处理。

具体的请求说明可以参考文档,这里给出一个完整的例子:

HTTP GET

URL:

https://www.googleapis.com/androidpublisher/v3/applications/安卓apk包名/purchases/products/在谷歌后台定义的商品id/tokens/安卓上报的token?access_token=上一步拿到的access_token

https://www.googleapis.com/androidpublisher/v3/applications/{$packageName}/purchases/products/{$productId}/tokens/{$token}?access_token={$accessToken}

请求成功后,在 json respond 中,获取到订单信息,具体内容说明可以查看文档: https://developers.google.com/android-publisher/api-ref/purchases/products#resource-representations其中有以下几个比较重要:

purchaseState : 仅为 0 时,为已支付状态acknowledgementState : 是否已确认。 确认操作可以由后端接口处理,下一步会介绍到

consumptionState : 是否已核销,商品核销只能由安卓处理,务必与安卓沟通好,确认 acknowledgementState 为 1 的时候才进行核销处理。 如果一次性商品不及时进行核销,用户无法操作第二次购买。

developerPayload : 载荷用于下一步的确认操作,请妥善保管。

purchaseType : 该字段有三个值,非必传字段,具体可以看文档。 比较重要的是为0时是沙箱(超级账号)支付,用户实际上是没有付款的。

orderId : 谷歌订单号,必须妥善保管

确认订单上一步中拿到的 developerPayload , 可以用于确认订单。一个订单只能确认一次,确认之后无法再次操作。 可以作为服务端确认凭证。

例如,我们有一个游戏装备商品,用户支付后,安卓上报 token ,后端确认 token ,记录好订单信息、做完业务处理之后处理确认订单,安卓再次跟谷歌确认订单是否为已确认(即acknowledgementState=1),然后安卓做装备发放处理并核销订单(即consumptionState=1),完成一次消费。

接口文档 : https://developers.google.com/android-publisher/api-ref/purchases/products/acknowledge

HTTP POST

URL:

https://www.googleapis.com/androidpublisher/v3/applications/{$packageName}/purchases/products/{$productId}/tokens/{$token}:acknowledge?access_token={$accessToken}

POST BODY:

developerPayload:上一步中拿到的 developerPayload请求成功后,HTTP 状态码为 204 ,没有 respond

至此,一次商品购买就完成了,辛苦了!

订单退款// todo

说点废话四月的小目标终于完成了... 本来想着写一篇有关 JWT 的使用介绍和demo的,但是突然公司这边谷歌内购的任务下来,就想着赶紧趁热把本篇撸出来了。 其实我还对接了 Firebase 的推送服务,也可以单独拉出来讲一讲。但是其实 Firebase 的对接也差不多内样,只是在 API Authorise 有一点坑,因为有几个接口谷歌都没有做更新,都是用的老版本,我苦读英文读了很长时间才搞懂... 其他就都还好,跟 Apple 的 APNS 差不了太多。

文章目录

2023-12-05 :

2021-08-19 10:22 更新

2021-05-18 16:06 更新

前言

账号配置

与 Google Play 绑定

启用 API

生成后端使用的凭证

网域验证

OAuth 同意屏幕设置

创建新的 OAuth 凭证

获取 refresh token

获取 access_token

支付流程

获取用户支付订单信息

确认订单

订单退款

说点废话