当前位置: 移动技术网 > 移动技术>移动开发>Android > Google支付从创建商品到支付成功踩过的坑

Google支付从创建商品到支付成功踩过的坑

2020年07月09日  | 移动技术网移动技术  | 我要评论

最近app需要上架到谷歌应用市场,必要条件是需要集成谷歌支付,于是开始一顿操作++++一堆怼脸型的bug解决过程,先从创建应用开始。

  1. 创建谷歌账号,并开通开发者权限,需要支付money,公司账号。
  2. 创建应用,应用提前准备好名称,图片等信息,开发人员需要打出一个release包,需要签名文件签名,注意版本号,测试阶段时,使用的版本号,不能高于谷歌平台上传的这个包。release包可以无内容,主要是包名和签名固定。
  3. 需要开发人员 准备谷歌的测试账号,实现不用支付即可完成支付流程。
  4. 创建应用-上传apk-提交内容详情内容-确定内容分级-选择发布范围,整个过程。创建过程中未截图保存内容,欢迎有遇到问题的朋友,评论区留言交流。
  5. 新版的谷歌支付已经废弃掉原有Google In-app Billing, 复制aidl文件到项目中的方式,目前使用 BillingClient 链接谷歌-查询产品-购买-消耗等一系列流程。

app内接入流程

1、添加依赖、添加权限。

  implementation 'com.android.billingclient:billing:3.0.0'
   <!--谷歌商店应用内购买结算需要的权限-->
    <uses-permission android:name="com.android.vending.BILLING" />
    <uses-permission android:name="com.farsitel.bazaar.permission.PAY_THROUGH_BAZAAR" />

2、创建连接。

    public void init() {
        mBillingClient = BillingClient.newBuilder(mActivityRef.get())
                .setListener(mPurchasesUpdatedListener)
                .enablePendingPurchases()
                .build();
        if (!mBillingClient.isReady()) {
            mBillingClient.startConnection(new BillingClientStateListener() {
                @Override
                public void onBillingSetupFinished(BillingResult billingResult) {
                    if (billingResult != null) {
                        if (billingResult.getResponseCode() == BillingClient.BillingResponseCode.OK) {
                            LogUtil.i(TAG, "onBillingSetupFinished==ok");
                        } else {
                            LogUtil.w(TAG, "onBillingSetupFinished--error==" + billingResult.getDebugMessage() + "====" + billingResult.getResponseCode());
                        }
                    } else {
                        LogUtil.w(TAG, "billingResult ==== null");
                    }

                }

                @Override
                public void onBillingServiceDisconnected() {
                    LogUtil.w(TAG, "onBillingServiceDisconnected");
                }
            });
        } else {
            LogUtil.w(TAG, "mBillingClient.isReady()  false");
        }
    }

3、购买

 /**
     * 购买
     */
    public void recharge() {
        if (mBillingClient.isReady()) {
            List<String> skuList = new ArrayList<>();
            skuList.add(mSku);//商品的id
            skuList.add("gas");// 这个参数不能为空,值随便传
            SkuDetailsParams.Builder params = SkuDetailsParams.newBuilder();
            params.setSkusList(skuList).setType(BillingClient.SkuType.INAPP);
//querySkuDetailsAsync 查询方法,list集合中传入商品id,谷歌后台-》应用内商品-》具体商品
            mBillingClient.querySkuDetailsAsync(params.build(),
                    new SkuDetailsResponseListener() {
                        @Override
                        public void onSkuDetailsResponse(BillingResult billingResult,
                                                         List<SkuDetails> skuDetailsList) {
                            if (billingResult.getResponseCode() == BillingClient.BillingResponseCode.OK
                                    && skuDetailsList != null) {
                                for (SkuDetails skuDetails : skuDetailsList) {
                            //  skuDetails 对象信息
//                        {
//                            "skuDetailsToken":"AEuhp4K_N_DyvTtZXkguU4XHEfLN2y54NJwxl9B5XxyVk1cvJ7Vkh-cZHpKEApKj3-il",
//                                "productId":"f0908u_",
//                                "type":"inapp",
//                                "price":"US$1.34",
//                                "price_amount_micros":1339320,
//                                "price_currency_code":"USD",
//                                "title":"VIP (Funchat)",
//                                "description":"Become VIP chatting with girls you like"
//                        }
                                    String sku = skuDetails.getSku();//商品id
                                    if (mSku.equals(sku)) {
                                        LogUtil.i(TAG, "sku can buy ");
                                        LogUtil.i(TAG, skuDetails.toString());
                                            //真正的购买方法
                                        BillingFlowParams purchaseParams =
                                                BillingFlowParams.newBuilder()
                                                        .setSkuDetails(skuDetails)
                                                        .build();
                                        mBillingClient.launchBillingFlow(mActivityRef.get(), purchaseParams);
                                    }
                                }
                            } else {
                                LogUtil.w(TAG, "goods search fail");
                            }
                        }
                    });

        } else {
            ToastUtil.toastShortMessage(mActivityRef.get().getString(R.string.google_connect_error));
        }
    }

4、购买回调接口,购买成功,调用消耗方法,不然会导致下次购买失败

    /**
     * 购买回调
     */
    private PurchasesUpdatedListener mPurchasesUpdatedListener = new PurchasesUpdatedListener() {
        @Override
        public void onPurchasesUpdated(BillingResult billingResult, List<Purchase> list) {
            String debugMessage = billingResult.getDebugMessage();
            LogUtil.e(TAG, "--》" + debugMessage);
            if (list != null && list.size() > 0) {
                if (billingResult.getResponseCode() == BillingClient.BillingResponseCode.OK) {
                    LogUtil.i(TAG, "购买成功,开始消耗商品");
                    for (Purchase purchase : list) {
                        mConsume = "2";
                        LogUtil.i(TAG, "PurchaseToken->" + purchase.getPurchaseToken());
                        consume(purchase.getPurchaseToken());
                    }
                }
            } else {
                switch (billingResult.getResponseCode()) {
                    case BillingClient.BillingResponseCode.SERVICE_TIMEOUT: {//服务连接超时
                        mListener.onState(mActivityRef.get(), RechargeResult.failOf("-3"));
                        mActivityRef.get().finish();
                        break;
                    }
                    case BillingClient.BillingResponseCode.FEATURE_NOT_SUPPORTED: {
                        mListener.onState(mActivityRef.get(), RechargeResult.failOf("-2"));
                        mActivityRef.get().finish();
                        break;
                    }
                    case BillingClient.BillingResponseCode.SERVICE_DISCONNECTED: {//服务未连接
                        mListener.onState(mActivityRef.get(), RechargeResult.failOf("-1"));
                        mActivityRef.get().finish();
                        break;
                    }
                    case BillingClient.BillingResponseCode.USER_CANCELED: {//取消
                        mListener.onState(mActivityRef.get(), RechargeResult.failOf("1"));
                        mActivityRef.get().finish();
                        break;
                    }
                    case BillingClient.BillingResponseCode.SERVICE_UNAVAILABLE: {//服务不可用
                        mListener.onState(mActivityRef.get(), RechargeResult.failOf("2"));
                        mActivityRef.get().finish();
                        break;
                    }
                    case BillingClient.BillingResponseCode.BILLING_UNAVAILABLE: {//购买不可用
                        mListener.onState(mActivityRef.get(), RechargeResult.failOf("3"));
                        mActivityRef.get().finish();
                        break;
                    }
                    case BillingClient.BillingResponseCode.ITEM_UNAVAILABLE: {//商品不存在
                        mListener.onState(mActivityRef.get(), RechargeResult.failOf("4"));
                        mActivityRef.get().finish();
                        break;
                    }
                    case BillingClient.BillingResponseCode.DEVELOPER_ERROR: {//提供给 API 的无效参数
                        mListener.onState(mActivityRef.get(), RechargeResult.failOf("5"));
                        mActivityRef.get().finish();
                        break;
                    }
                    case BillingClient.BillingResponseCode.ERROR: {//错误
                        mListener.onState(mActivityRef.get(), RechargeResult.failOf("6"));
                        mActivityRef.get().finish();
                        break;
                    }
                    case BillingClient.BillingResponseCode.ITEM_ALREADY_OWNED: {//未消耗掉
                        mConsume = "1";
                        queryHistory();
                        break;
                    }
                    case BillingClient.BillingResponseCode.ITEM_NOT_OWNED: {//不可购买
                        mListener.onState(mActivityRef.get(), RechargeResult.failOf("8"));
                        mActivityRef.get().finish();
                        break;
                    }
                }
            }
        }
    };

5、消耗

    /**
     * 消耗
     */
    private void consume(String purchaseToken) {
        // 只有消费成功之后,才能真正到账,否则3天之后,会执行退款处理 测试阶段只有5分钟
        ConsumeParams consumeParams =
                ConsumeParams.newBuilder()
                        .setPurchaseToken(purchaseToken)
                        .build();
        mBillingClient.consumeAsync(consumeParams, new ConsumeResponseListener() {

            @Override
            public void onConsumeResponse(BillingResult billingResult, String s) {
                Log.e(TAG, "onConsumeResponse code = " + billingResult.getResponseCode() + " ,  msg = " + billingResult.getDebugMessage() + " , purchaseToken = " + purchaseToken);              // 消费成功  处理自己的流程,我选择先存入数据库
                LogUtil.w(TAG, "-->" + s);
                if (billingResult.getResponseCode() == BillingClient.BillingResponseCode.OK) {
                    LogUtil.i(TAG,"consume  success ");
                }
            }
        });
        //上传服务器验证
//        uploadToServer(purchaseToken, mOrderID, mPayTest);

    }

 

 

错误1:此版本的应用未配置为通过GooglePlay结算。有关详情,请访问帮助中心。

app内错误截图

出现问题原因

  • 是打包的时候,versionCode的值比提交到google play后台的版本要高。
  • 打包的时候,和google play后台上的包的签名不一致,APK与发布证书一起签署。(重要提示:使用“Google Play应用程序签名”时,只有直接从Google PlayStore下载才有效!
  • 登录测试机已登录谷歌账号,并已添加到谷歌测试账号中,添加地址  https://play.google.com/apps/testing/包名
  • 确认账号信息里可用于测试的Gmail账号里,已添加测试账号。

错误2:应用内无法查询商品id,无法吊起支付窗口

一定要等你的应用为**Published**状态之后,并且创建了应用内商品为已激活状态,在app里面才能查到商品id,执行支付等操作,否则怎么样都查不到

  • 应用已经发布了,但是还是吊不起支付窗口

首先app需要安装google三件套,不知道怎么安装的,可以安装一个YouTube,进入app后会自动提示你需要安装google play,需要vpn,然后一定注意了,需要在权限设置里面,把google play的##允许应用在后台弹窗界面##这个权限打开,一定记得要打开

  • 当一切准备就绪之后,报:目前还无法在您所在的国家/地区购买Google Play中的内容。这个因为在中国不允许。

网页登录你的google账户:在设置里面,把你的地址改成美国或其他支持的国家,然后清除app内google play的数据,重新进入,重新选择地区(刚才你修改的地区),选完之后会提示你切换到美国的商店,然后再添加付款信息(中国的卡就行,我用的是招商银行的信用卡),这样就万事大吉了,之后就可以正常支付了。

错误3:In-app billing API version 3 is not supported on this device.

该手机登录Google账号的问题,或者说是Google账号的归属地问题,如果之前是ok的,突然报这样的的问题,重启,重启,重启 !!!包括电脑。至于哪些地方不能使用,我没有足够的账号数据支撑。或许咱们能做的是在产品角度,给出相应提示,例如更换账号啥的。

错误4:signInResult:failed code=12501

先检查网络是否墙了

流程跑通,放鞭炮,现在回顾来看,其实还挺简单的,最最最前提的条件是,翻墙成功,测试账号信息完善,会省80%的工作量。
 

本文地址:https://blog.csdn.net/lxm20819/article/details/107141822

如对本文有疑问, 点击进行留言回复!!

相关文章:

验证码:
移动技术网