You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

StoreKit订阅过期观测及Transaction.currentEntitlements调用相关问题

StoreKit 在 ObservableObject 中的适配疑问解答

我在适配StoreKit到ObservableObject模型时存在一些困惑。按照我的理解,如果应用启动时订阅处于激活状态,但后续订阅失效,唯一的检测方式是调用Transaction.currentEntitlements并检查订阅的currentEntitlements是否为.verified。

以下是我的两个疑问及对应的解答:

疑问一:检查当前订阅状态时是否需要调用finish()?

我写了这样的检查方法,不确定是否要在verified分支里调用finish():

private func isPurchased(product: Product) async -> Bool {
    guard let state = await product.currentEntitlement else {
        return false
    }
    
    switch state {
    case .unverified(_, _):
        return false
    case .verified(let verifiedProduct):
        // Necessary??
        await verifiedProduct.finish()
        return true
    }
}

解答:不需要在这里调用finish()。
Transaction.finish()的核心作用是通知StoreKit:你已经完成了该交易的业务处理(比如给用户解锁功能、记录购买记录),避免StoreKit重复推送该交易事件。而currentEntitlements返回的是当前有效的订阅权益凭证,这类凭证不需要被"结束"——它们只是用来确认用户当前是否拥有权限的依据。

只有在处理Transaction.updates流中的交易事件(比如新购买成功、订阅自动续期、用户申请退款等)时,才需要在完成对应业务逻辑后调用finish()。

疑问二:何时调用Transaction.currentEntitlements?有没有可观测的状态变化机制?

我需要在订阅过期时立即更新UI,但不确定StoreKit是否提供了可观测的机制,难道必须用定时器频繁检查Transaction.currentEntitlements?

解答:不需要定时器轮询,StoreKit提供了原生的状态更新监听机制:

  • 监听Transaction.updates异步流:这个流会在订阅状态发生变更时(包括订阅过期、续期、退款、权限恢复等)自动推送交易事件。你可以在ObservableObject的初始化方法中启动监听,一旦收到事件就更新本地的订阅状态变量,触发UI刷新。
  • 应用启动时调用一次:用来初始化当前的订阅状态,确保应用启动时UI能正确显示用户的权限情况。
  • 应用从后台回到前台时调用一次:补充兜底,避免订阅在后台过期后,前台UI没能及时同步状态。

定时器轮询不仅会增加不必要的网络开销,还可能导致UI更新延迟,优先使用Transaction.updates流是更高效可靠的方案。


内容的提问来源于stack exchange,提问作者CalebK

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.06.12 14:49:57