0

I have one weird issue right now. I am using DispatchGroup() to verify in-app subscriptions on load. It works only if I have already authenticated with apple id.

    let dispatchGroup = DispatchGroup()

    var index = 0  // <--- Just For test
    for a in inAppPurchaseIds {
        index = index + 1
        print("INDEX ENTER --> \(index)")
        dispatchGroup.enter()   // <<---

        MPInAppPurchases.verifySubscription(a) { [weak self] status, data, error, expDate in
            print("LOOP COUNT --> YES")

            guard let me  = self else {
                print("INDEX LEAVE ME --> \(a)")

                dispatchGroup.leave()
                return
            }

            print("DATA ---- \(String(describing: data))")

            print("INDEX LEAVE --> \(a)")

            dispatchGroup.leave()
        }
    }

    dispatchGroup.notify(queue: .main) {
        print("NOTIFY")
    }

Function that verifies receipt

 static func verifySubscription(_ id: String, completion: purchaseHandler?) {
    let appleValidator = AppleReceiptValidator(service: .production, sharedSecret: sharedSecret)
    SwiftyStoreKit.verifyReceipt(using: appleValidator) { result in
        switch result {
        case .success(let receipt):
            // Verify the purchase of a Subscription
            let purchaseResult = SwiftyStoreKit.verifySubscription(
                ofType: .autoRenewable, // or .nonRenewing (see below)
                productId: id,
                inReceipt: receipt)

            switch purchaseResult {
            case .purchased(let expiryDate, _):
                print("\(id) is valid until \(expiryDate)")
                completion?(true, "Product Purchased", nil, expiryDate)
            case .expired(let expiryDate, _):
                print("\(id) is expired since \(expiryDate)")
                completion?(false, "Product Expired", nil, expiryDate)
            case .notPurchased:
                print("The user has never purchased \(id)")
                completion?(false, "Product Not Purchased", nil, nil)
            }

        case .error(let error):
            print("Receipt verification failed: \(error)")
            completion?(false, "Receipt verification failed", error.localizedDescription, nil)
        }
    }
}

LOG

INDEX ENTER --> 1
INDEX ENTER --> 2
INDEX ENTER --> 3

LOOP COUNT --> YES
DATA ---- Optional("Product Not Purchased")
INDEX LEAVE --> kr.co.proPackage

The function returns data on completion but here I am unable to get any data from the function and only once it leaves the group. Any idea why this happens? This does happens only when I am not logged in with my apple id in my device. Once its done, it works perfectly.

Steps to reproduce the issue

Log out from my apple id > remove an app from my device > relaunch the app.

Bhavin Bhadani
  • 22,224
  • 10
  • 78
  • 108
  • 1
    You need to look into `SwiftyStoreKit.verifyReceipt` - It seems that it doesn't always call the completion handler. Perhaps it doesn't handle concurrent operation correctly? – Paulw11 Mar 22 '19 at 08:02
  • The following is strange: Before printing `LOOP COUNT --> YES`, I would expect some print statement from the `verifySubscription` function, like `\(id) is valid until` or `Receipt verification failed` or something. Could you add print statements at the beginning and at the end of that very function and post that output? – Andreas Oetjen Mar 22 '19 at 08:06
  • @AndreasOetjen I have just removed that line from log to make it easy for Q&A. – Bhavin Bhadani Mar 22 '19 at 08:07
  • @Paulw11 Ahh maybe. But it does work after we authenticate to apple id. why so? – Bhavin Bhadani Mar 22 '19 at 08:08
  • This is the log once I authenticate with apple id. https://paste.ubuntu.com/p/H5SDf2ZHyR/ – Bhavin Bhadani Mar 22 '19 at 08:26
  • I can see SwiftStoreKit is open source so you can actually try putting debug points and see whether completion block is getting called or not. My guess is they are not getting called. Also, can you confirm if an Apple ID login screen is getting shown or not? Because when you are logged out and try to verify script, it should. – Puneet Sharma Mar 22 '19 at 09:52
  • @PuneetSharma If that so then how does it call on other occasion? – Bhavin Bhadani Mar 22 '19 at 10:06
  • It depends whether SKReceiptRefreshRequest calling its delegate(SKRequestDelegate) methods or not. I believe if you try debug points, you may get some answers – Puneet Sharma Mar 22 '19 at 10:10
  • @PuneetSharma ok – Bhavin Bhadani Mar 22 '19 at 10:19
  • FWIW, I suspect a bug in SwiftyStoreKit. See my comment to an old issue, https://github.com/bizz84/SwiftyStoreKit/issues/388#issuecomment-517413021. – Rob Aug 01 '19 at 18:53
  • @Rob yes I do think so... What I did was calling `verifyGroupSubscription` in the previous controller and that way its working fine. Though I don't think its great solution but it works for me at least for now. – Bhavin Bhadani Aug 02 '19 at 03:44

0 Answers0