如果您正在使用服务器端收据验证,是否有必要刷新收据?

Is it ever necessary to refresh receipt if you are using doing server-side receipt validation?

我创建了一个具有自动续订订阅功能的应用程序。

以下是我用来了解用户是否有有效订阅的逻辑。


App Store 审核多次拒绝我的应用程序,因为 SKReceiptRefreshRequest 错误。我无法重现 App Store 审查委员会面临的错误。

在网上搜索解决问题的过程中,我了解了以下关于本地收据的事实-

从以上2条信息,我推断在生产环境中没有必要调用SKReceiptRefreshRequest因为App Store服务器会提供最新的细节,即使本地收据是旧的和本地的生产中始终存在收据。


为了让我的应用程序通过 App Store 审核,我决定删除 SKReceiptRefreshRequest,因为它会在 Testflight 构建中给出错误,并且在生产中不需要。

任何人都可以确认我这样做是否正确吗?

我已经通过以下方式生成收据并将生成的收据发送到服务器进行验证:

https://developer.apple.com/documentation/storekit/in-app_purchase/validating_receipts_with_the_app_store

你的逻辑有多个缺陷:

1) paymentQueue(_:updatedTransactions:) 在后台调用并且(据我所知)已经更新了本地收据。此外,从 App Store 下载的应用程序始终包含收据。所以没有必要在那个方法中调用SKReceiptRefreshRequest

2) SKReceiptRefreshRequest 要求用户输入他的密码以允许收据刷新。由于您触发了 paymentQueue(_:updatedTransactions:) 内的方法,该方法在后台调用,我认为这就是刷新请求失败并且 Apple 拒绝您的应用程序的问题。尽管如此,这种方法有其存在的理由:在生产中,您需要它来允许用户在重新安装应用程序或在其他设备上恢复购买,并且对于调试和 TestFlight 构建,您需要它来获取最新的收据。

3) 您不应将收据从您的应用程序发送到 Apple 的端点

Warning

Do not call the App Store server verifyReceipt endpoint from your app. You can't build a trusted connection between a user’s device and the App Store directly, because you don’t control either end of that connection, which makes it susceptible to a man-in-the-middle attack.

Source

如何进行?

我建议做以下事情:

1) 不要在paymentQueue(_:updatedTransactions:)

中触发SKReceiptRefreshRequest

2) 如果尚未完成,请在您的应用中提供一个 "restore purchases" 按钮(调用 SKReceiptRefreshRequest

3) 实施 local or server-to-server 收据验证