google 内购记录

1.GooglePlay内购服务器验单配置 (新版本好像不需要API 配置关联,好像不需要了)

详细配置url: https://blog.csdn.net/wuyutaoktm/article/details/122450878

2. 用golang代码实现,主要是验证订单和发币,PAY_JSON 是上一个步骤申请的

func verifyAndConsumePurchase(info *PurchaseInfo) (bool, error, int8) {ctx := context.Background()rawByte, _ := json.Marshal(info)googlePayLog := &handler.GooglePayLog{UserID:            info.UserId,Raw:               string(rawByte),RespRaw:           "",PurchaseTokenMD5:  "",CheckStatus:       -1,ConsumptionStatus: -1,GoldStatus:        -1,RechargeID:        0,MsgErr:            "",}// 使用服务账号创建凭证conf, err := google.JWTConfigFromJSON([]byte(PAY_JSON), androidpublisher.AndroidpublisherScope)if err != nil {googlePayLog.MsgErr = "1:" + err.Error()db_common.ApplyInsertGooglePayLog(googlePayLog)zlog.F().Errorf("user_id:%d,producd_id:%s,%v", info.UserId, info.ProductID, googlePayLog.MsgErr)return false, err, 0}// 使用凭证创建Google Play Developer服务service, err := androidpublisher.NewService(ctx, option.WithTokenSource(conf.TokenSource(ctx)))if err != nil {googlePayLog.MsgErr = "2:" + err.Error()db_common.ApplyInsertGooglePayLog(googlePayLog)zlog.F().Errorf("user_id:%d,producd_id:%s,%v", info.UserId, info.ProductID, googlePayLog.MsgErr)return false, err, 0}// 调用API验证购买call := service.Purchases.Products.Get(info.PackageName, info.ProductID, info.PurchaseToken)response, err := call.Do()if err != nil {googlePayLog.MsgErr = "3:" + err.Error()db_common.ApplyInsertGooglePayLog(googlePayLog)zlog.F().Errorf("user_id:%d,producd_id:%s,%v", info.UserId, info.ProductID, googlePayLog.MsgErr)return false, err, 1}str, _ := json.Marshal(response)zlog.F().Infof("userId:%d,productId:%d,response: %+v", info.UserId, info.ProductID, str)//0:表示交易已成功,并且商品未被消费。//1:表示交易被取消。//2:可能表示交易被拒绝,或某些其他的错误状态。// 验证购买状态:0表示购买成功if response.PurchaseState != 0 {zlog.F().Errorf("user_id:%d,producd_id:%s,PurchaseState:%d", info.UserId, info.ProductID, response.PurchaseState)googlePayLog.CheckStatus = int8(response.PurchaseState)googlePayLog.PurchaseTokenMD5 = utils.Md5(response.PurchaseToken)db_common.ApplyInsertGooglePayLog(googlePayLog)return false, nil, 0}// 调用API确认消费(消耗商品)//consumeCall := service.Purchases.Products.Acknowledge(info.PackageName, info.ProductID, info.PurchaseToken, &androidpublisher.ProductPurchasesAcknowledgeRequest{})consumeCall := service.Purchases.Products.Consume(info.PackageName, info.ProductID, info.PurchaseToken)if err := consumeCall.Do(); err != nil {googlePayLog.CheckStatus = int8(response.PurchaseState)googlePayLog.PurchaseTokenMD5 = utils.Md5(response.PurchaseToken)googlePayLog.ConsumptionStatus = 0 // 0表示消费失败googlePayLog.MsgErr = "4:" + err.Error()db_common.ApplyInsertGooglePayLog(googlePayLog)zlog.F().Errorf("user_id:%d,producd_id:%s,%v", info.UserId, info.ProductID, googlePayLog.MsgErr)return false, err, 1}// 加币操作if err = dealMysql(info, googlePayLog); err != nil {googlePayLog.CheckStatus = int8(response.PurchaseState)googlePayLog.PurchaseTokenMD5 = utils.Md5(response.PurchaseToken)googlePayLog.ConsumptionStatus = 1 // 1表示消费失败googlePayLog.GoldStatus = 0        // 0 加币失败googlePayLog.MsgErr = "5:" + err.Error()db_common.ApplyInsertGooglePayLog(googlePayLog)zlog.F().Errorf("user_id:%d,producd_id:%s,%v", info.UserId, info.ProductID, googlePayLog.MsgErr)return false, err, 1} else {// successgooglePayLog.CheckStatus = int8(response.PurchaseState)googlePayLog.PurchaseTokenMD5 = utils.Md5(response.PurchaseToken)googlePayLog.ConsumptionStatus = 1 // 1表示消费失败googlePayLog.GoldStatus = 1        // 0 加币失败db_common.ApplyInsertGooglePayLog(googlePayLog)}return true, nil, 0
}

3. 注意丢单情况,改成客户端主动查询丢单

丢单因为主要是因为支付操作都是在客户端完成的,非常容易受到网络等因素的影响,造成互相通信失败。比如:用户确认支付后,把请求提交给google play,可能因为网络不好造成,客户端没有接收到支付成功能消息(但有可能已经支付成功了,只是没收到支付结果而已);还有客户端把支付结果通知给服务器时,也有可能因丢包等问题造成通知失败。
在这里插入图片描述

4. 官网服务端api

api接口,get 和 确认消耗consume

服务端api官网地址: https://developers.google.com/android-publisher/api-ref/rest/v3/purchases.products/consume?hl=zh-cn

安卓api:
https://developer.android.com/reference/com/android/billingclient/api/BillingFlowParams.Builder#setobfuscatedaccountid

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/news/605795.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

Java后端开发——Ajax、jQuery和JSON

Java后端开发——Ajax、jQuery和JSON 概述 Ajax全称是Asynchronous Javascript and XML,即异步的JavaScript和 XML。Ajax是一种Web应用技术,该技术是在JavaScript、DOM、服务器配合下,实现浏览器向服务器发送异步请求。 Ajax异步请求方式不…

螺纹钢负公差测径仪获得哪些信息?

螺纹钢负公差轧制是很多厂家在使用的一种轧制方式,蓝鹏测控在推出普通型轧钢测径仪和智能型轧钢测径仪后,又推出了可显示负公差信息的测径仪,本文来简单看一下螺纹钢负公差轧制能从测径仪中获得哪些信息? 负公差测径仪为了能对螺纹…

Java+springboot+vue智慧校园源码,数据云平台Web端+小程序教师端+小程序家长端

技术架构: Javaspringbootvue element-ui小程序电子班牌:Java Android演示自主版权。 智慧校园电子班牌人脸识别系统全套源码,包含:数据云平台Web端小程序教师端小程序家长端电子班牌 学生端。 电子班牌系统又称之为智慧班牌&am…

什么是本地存储的有效期?

本地缓存设置有效期? 使用localStorage本地缓存存储数据时不能像cookie那样设置有效期,使得数据会一直存在浏览器中,除非人为删除。这时我们可以封装一下localStorage,在需要有效期的数据存储时同时设置到期时间,读取的…

2024 极术通讯-AI 2024:端、边AI将成为硬件厂商布局重点

导读:极术社区推出极术通讯,引入行业媒体和技术社区、咨询机构优质内容,定期分享产业技术趋势与市场应用热点。 芯方向 Helium 技术讲堂 | 为何不直接采用 Neon? 当人工智能 (AI) 下沉到各式各样的应用当中,作为市场…

【设计模式之美】SOLID 原则之三:里式替换(LSP)跟多态有何区别?如何理解LSP中子类遵守父类的约定

文章目录 一. 如何理解“里式替换原则”?二. 哪些代码明显违背了 LSP?三. 回顾 一. 如何理解“里式替换原则”? 子类对象能够替换程序中父类对象出现的任何地方,并且保证原来程序的逻辑行为不变及正确性不被破坏。 里氏替换原则…

Sui链上铭文爆火,TPS近6000领先同行

在2023年接近尾声时,用户涌入众多智能合约平台进行铭文相关交易,无意中对各种网络进行了压力测试。在许多平台出现拥堵和费用飙升的情况下,Sui通过实现令人印象深刻的TPS,在没有减速或gas费用激增的情况下脱颖而出。 最初用于比特…

人工智能(AI)在未来电影制作业中的革命性影响及挑战

随着人工智能(AI)技术的不断突破,其对电影制作行业的改造和影响日益显著。本文旨在深入探讨AI在未来的应用将如何重塑电影制作流程、提升作品质量,并同时面对的挑战与变革。 一、优化电影制作流程与降低成本 AI在电影制作中的应用…

vue3+vite +element plus日历date picker中文显示

项目情况 element-plus 默认是英文模式,需要中文模式的话需要设置一下: 项目框架(vue3):vite JS element-plus 版本:(注意版本兼容,element plus 较低版本:1.xx.xx&a…

Docker 容器管理和镜像管理基础知识(二)

Docker 容器管理和镜像管理 容器管理 docker create 命令用于在 Docker 中创建一个新的容器,但不会自动启动它。这个命令会返回容器的 ID,可以使用它来 进一步操作容器,这也是与 docker run 命令的一个区别 以下是 docker create 的基本用…

Kotlin 作用域函数

作用域函数(Scope Functions) 函数参数返回值说明letitlambda result非空对象执行代码块applythis上下文对象用于对象配置操作alsoit上下问对象执行额外操作runthislambda result用于对象配置和计算结果withthislambda result非扩展函数,配置…

STL标准库与泛型编程(侯捷)笔记3

STL标准库与泛型编程(侯捷) 本文是学习笔记,仅供个人学习使用。如有侵权,请联系删除。 参考链接 Youbute: 侯捷-STL标准库与泛型编程 B站: 侯捷 - STL Github:STL源码剖析中源码 https://github.com/SilverMaple/STLSourceCo…

中国式浪漫:古人对万物的雅称

古人对万物的称呼都是美而浪漫,在诗词中,女子被称为红妆、佳人、婵娟、碧玉、红颜。雪也叫作琼芳、玉絮、六花、玉鸾;在诗词中,每一缕风,每一片雪,都有一个雅致的名字。所谓的诗情画意,便是用普…

基于深度学习的停车位关键点检测系统(代码+原理)

摘要: DMPR-PS是一种基于深度学习的停车位检测系统,旨在实时监测和识别停车场中的停车位。该系统利用图像处理和分析技术,通过摄像头获取停车场的实时图像,并自动检测停车位的位置和状态。本文详细介绍了DMPR-PS系统的算法原理、…

最短路径问题相关算法、原理及适用场景

这里写目录标题 一、最短路径算法、原理及适用场景深度优先搜索算法/广度优先搜索算法Floyd算法(Floyd-Warshell算法)Dijkstra算法A*算法贝尔曼福特算法(Bellman-Ford Algorithm)SPFA算法(Shortest Path Faster Algori…

FPGA高端项目:纯verilog的 25G-UDP 高速协议栈,提供工程源码和技术支持

目录 1、前言免责声明 2、相关方案推荐我这里已有的以太网方案本协议栈的 1G-UDP版本本协议栈的 10G-UDP版本1G 千兆网 TCP-->服务器 方案1G 千兆网 TCP-->客户端 方案10G 万兆网 TCP-->服务器客户端 方案 3、该UDP协议栈性能4、详细设计方案设计架构框图网络调试助手…

传感数据分析——小波滤波

传感数据分析——小波滤波 文章目录 传感数据分析——小波滤波前言一、运行环境二、Python实现总结 前言 小波滤波算法是一种基于小波变换的滤波方法,其核心思想是将信号分解成不同的频率成分,然后对每个频率成分进行独立的处理。小波滤波器的设计和应用…

第12课 实现桌面与摄像头叠加

在上一节,我们实现了桌面捕获功能,并成功把桌面图像和麦克风声音发送给对方。在实际应用中,有时候会需要把桌面与摄像头图像叠加在一起发送,这节课我们就来看下如何实现这一功能。 1.备份与修改 备份demo11并修改demo11为demo12…

安达发|基于APS排程系统的PDM功能

APS系统(Advanced Planning and Scheduling,先进计划与排程)是一种基于APS系统(Advanced Planning and Scheduling,先进计划与排程)是一种基于供应链管理和生产管理的综合性软件系统。它通过整合企业内外部…

在anaconda中安装pytorch的GPU版本

本文前提: 1.你已经下载好了anaconda,最好是新建一个虚拟环境来安装pytorch的GPU版本,并且设置了国内镜像源; 2.了解自己电脑对应的cuda版本,可通过nvidia-smi,并下载好了cuda。 安装pytorch的GPU版本 到官网中https…