尧图建网站 尧图建网站 YAOTU WEB BUILD 免费咨询
ARTICLE DETAIL

资讯详情

深耕网站建设与建站编程的一线实战洞察。

如何防止内购破解与白嫖?flutter_inapp_purchase服务端收据验证完全指南

如何防止内购破解与白嫖?flutter_inapp_purchase服务端收据验证完全指南 如何防止内购破解与白嫖flutter_inapp_purchase服务端收据验证完全指南【免费下载链接】flutter_inapp_purchaseFlutter In App Purchase plugin that confirms OpenIAP项目地址: https://gitcode.com/gh_mirrors/fl/flutter_inapp_purchase在 Flutter 应用中做内购In-App Purchase最容易被忽视的坑就是只在客户端判断用户是否买过结果被破解者绕过免费白嫖你的付费功能。本文将用 flutter_inapp_purchase 这个 OpenIAP 兼容的内购插件手把手讲清楚服务端收据验证Receipt Validation的完整流程iOS 的收据数据、Android 的 purchaseToken、第三方验证服务以及一套防止白嫖的完整安全清单。为什么客户端验证防不住白嫖很多新手会这样写逻辑用户点击购买 → 收到购买成功事件 → 直接解锁付费功能。这个流程在正常设备上没问题但存在两个致命漏洞重放与伪造客户端代码运行在用户设备上攻击者可以通过 Hook、重放旧的购买成功事件让 App 误以为完成了付费跳过购买流程只要解锁状态存在本地比如 SharedPreferences 里存了个isVip true改一个字节就能永久免费使用。唯一可靠的防线是由你的后端服务器向 Apple / Google 官方验证收据的真实性只有服务器确认通过后才下发权益。这就是服务端收据验证的核心思想。flutter_inapp_purchase 在设计上已经为这条防线做好了准备所有购买事件都会携带可验证的凭证字段验证失败前你绝不应该发货。两个平台两种验证凭证iOS 和 Android 的收据格式完全不同但插件把它们统一收敛到了Purchase对象上定义见lib/types.dart事件分发逻辑在lib/flutter_inapp_purchase.dart对比项iOS / macOSAndroid核心凭证收据数据transactionReceipt / JWS 字符串purchaseToken购买令牌官方验证服务App Store Server API / verifyReceiptGoogle Play Developer API验证发起方你的后端用 Apple 公钥或 Apple 接口你的后端OAuth 2.0 服务账号关键方法validateReceiptIOS()、getReceiptDataIOS()verifyPurchase()google 参数 记住一句话iOS 验收据Android 验令牌但都必须在你自己的服务器上完成。第一步拿到可验证的收据数据无论哪个平台第一步都是把凭证从插件里取出来。有两种方式1. 监听购买事件新购买时触发通过purchaseUpdatedListener流每笔新交易都会带一个Purchase对象其中包含productId产品 IDSKUtransactionId交易唯一标识transactionReceiptiOS/purchaseTokenAndroid服务端验证用的凭证2. 拉取已有购买App 启动/恢复购买时调用getAvailablePurchases()插件会自动向商店查询该用户当前所有有效权益——iOS 底层对应 StoreKit 2 的Transaction.currentEntitlementsAndroid 会自动合并查询一次性产品和订阅两个列表。这一步既能做恢复购买也是防止用户换机/重装后凭证丢失的关键。final purchases await iap.getAvailablePurchases(); for (final p in purchases) { // iOS: p.transactionReceiptJWS // Android: p.purchaseToken // 把凭证发到你的服务器去验证而不是在本地解锁功能 }iOS收据验证的正确姿势iOS 端插件提供了validateReceiptIOS()方法源码实现见ios/Classes/FlutterInappPurchasePlugin.swift它基于 StoreKit 2 完成本地初步校验并返回一个包含jwsRepresentation的结果对象——这个 JWS 字符串就是你应该发给服务器的凭证。⚠️ 注意插件文档中明确标注本地校验仅用于测试LOCAL TESTING ONLY。生产环境的流程应该是客户端把jwsRepresentation或transactionReceipt连同产品 ID 发给你的后端后端用 Apple 的公钥验证 JWS 签名或调用 Apple 官方验证接口验证响应中status 0表示收据有效还要检查交易状态是否已退款revoked、是否过期后端确认后向客户端返回签名过的权益凭证客户端凭此解锁功能。另外沙盒测试收据与正式收据的环境不同服务端要处理好21007沙盒收据发到正式接口/21008正式收据发到沙盒接口这类状态码自动切换验证端点重试。AndroidpurchaseToken 官方开发者 APIAndroid 端不走收据概念而是每笔购买对应一个 purchaseToken。插件在 Android 侧已自动完成购买数据的校验与合并实现见android/src/main/kotlin/io/github/hyochan/flutter_inapp_purchase/AndroidInappPurchasePlugin.kt并把purchaseToken暴露给 Dart 层。服务端验证流程用 Google 服务账号走 OAuth 2.0 获取 access token只放在服务器上绝不能打进客户端后端调用 Google Play Developer API用packageName productId purchaseToken查询这笔购买一次性产品检查purchaseState0 表示已购买订阅还要检查expiryTimeMillis是否已过期、是否处于宽限期。插件也提供了verifyPurchase()方法配合google参数传入 packageName 和 purchaseToken 等方便你在调试期快速打通验证链路但同样建议生产环境走你自己的后端。 补充一点插件遵循 OpenIAP 开放内购标准除了 Apple / Google其verifyPurchase()还提供horizon参数可面向 Horizon OS 等更多平台扩展统一的验证模型。不想自己写后端用第三方验证服务自己实现双端签名验证、处理退款和宽限期状态其实工作量不小。插件内置了verifyPurchaseWithProvider()方法可以直接对接第三方验证服务如 IAPKit把 JWS / purchaseToken 发给它做权威校验返回统一的状态验证状态含义你应该怎么做entitled权益有效解锁功能expired已过期撤销权益canceled用户取消可能仍有剩余时间展示续费引导pending-acknowledgment待确认Android调用finishTransaction()inauthentic验证失败可能是伪造拒绝发货并记录日志对于小团队这是一条低成本拿到企业级验证的捷径对于有后端团队的项目自建验证服务则能完全掌控数据。防止白嫖的 7 条安全清单结合 收据验证 API 文档 的最佳实践上线前请逐条自查✅验证通过前绝不发货——解锁状态以服务器为准客户端只做展示✅客户端验证仅用于开发调试生产必须走服务器✅验证成功后再调用finishTransaction()——iOS 用它出队Android 对消费型产品会消耗、对非消费型产品会确认Android 必须在 3 天内确认否则商店会退款✅凭证不要落本地明文存储——收据/token 存服务器本地只存服务器签发的权益✅密钥永远只在服务端——iOS 的 shared secret、Google 的 OAuth 服务账号都不能出现在客户端代码里✅处理退款与订阅生命周期——revoked退款、inGracePeriod宽限期状态要正确回收权益✅App 启动时重新对账——尤其 Android订阅在 App 关闭期间续费不会触发purchaseUpdatedListener事件必须主动调用getAvailablePurchases()并向服务器重新验证否则用户会莫名失去会员。常见疑问 FAQQ我已经调用了validateReceiptIOS()且返回有效还需要服务器验证吗需要。本地校验只能验证 JWS 是否来自 Apple 签名无法覆盖退款、取消、过期等完整业务状态且本地逻辑可被绕过。它适合开发调试生产请以服务器结论为准。Q验证失败了还能重试吗能。保持交易不 finish在purchaseErrorListener中捕获错误错误码定义见lib/enums.dart对网络类错误做指数退避重试即可。Q一次性产品和订阅的验证区别是什么一次性产品验证后关注是否已消费Android 消费后可重复购买订阅还要持续跟踪续费、到期、宽限期状态推荐配合getActiveSubscriptions()和 iOS 的subscriptionStatusIOS()获取细分阶段试用期、宽限期等。总结防止内购破解的公式其实很简单客户端只负责把凭证交出去服务器负责验真伪、发权益iOS 交 JWS 收据、Android 交 purchaseToken验证通过才 finish 交易。flutter_inapp_purchase 已经把这些凭证和验证接口全部准备好——getAvailablePurchases()取证、validateReceiptIOS()调 iOS 链路、verifyPurchase()打通 Android 链路、verifyPurchaseWithProvider()一键接入第三方验证。把这套流程跑通你的付费功能就基本告别白嫖了。【免费下载链接】flutter_inapp_purchaseFlutter In App Purchase plugin that confirms OpenIAP项目地址: https://gitcode.com/gh_mirrors/fl/flutter_inapp_purchase创作声明:本文部分内容由AI辅助生成(AIGC),仅供参考
返回列表