react-native-iap: [8.0.4][iOS] finishTransaction promise never finishes

Version of react-native-iap

8.0.4

Version of react-native

0.67.2

Platforms you faced the error (IOS or Android or both?)

iOS

Expected behavior

calling finishTransaction marks the transaction as finished

Actual behavior

Any code after the await RNIap.finishTransaction is not executed, and the transaction is reattempted after each relaunch of the app.

Tested environment (Emulator? Real Device?)

Real device

Steps to reproduce the behavior

Purchase a product in sandbox, call finishTransaction, check if some code after the promise is executed.

Here is my listener:

purchaseUpdatedListener = RNIap.purchaseUpdatedListener(
    async (purchase: RNIap.InAppPurchase | RNIap.SubscriptionPurchase) => {
      const receipt = purchase.transactionReceipt;

      try {
        if (receipt) {
          const decodedReceipt = await decodeAppleReceipt(receipt);
          const isValid = await isSubValid(decodedReceipt);

          if (isValid) {
            const { latest_receipt_info: latestReceipts }: any = decodedReceipt;
            const sortedReceiptInfo = latestReceipts.sort(
              (
                a: { original_purchase_date_ms: number },
                b: { original_purchase_date_ms: number },
              ) => b.original_purchase_date_ms - a.original_purchase_date_ms,
            );
            let latestReceiptInfo = sortedReceiptInfo[sortedReceiptInfo.length - 1];
            console.log(latestReceiptInfo);

            const subPrice = await getSubPrice(latestReceiptInfo.product_id);
            const subDuration = getSubDuration(latestReceiptInfo.product_id);

            latestReceiptInfo = {
              ...latestReceiptInfo,
              subscription_price: subPrice,
            };

            // Persist the purchase on backend API
            const persistedPurchase = await persistSubscriptionIOS(latestReceiptInfo, sessionId);
            const persistedPurchaseId: string = persistedPurchase.persistPurchase.id;

            latestReceiptInfo = {
              ...latestReceiptInfo,
              persisted_purchase_id: persistedPurchaseId,
              source: 'ios',
              subscription_duration: subDuration,
            };


            // Activate the subscription on backend API
            const deliveryResult = await activateSubscription(latestReceiptInfo, sessionId);

            if (isSuccess(deliveryResult)) {
              console.log('deliveryResult is true');
              await RNIap.finishTransaction(purchase, false);
              console.log('finish transaction done');
              onSuccess?.();
            }
          }
        }
      } catch (error) {
        console.error(error);
      }
    },
  );

The console.log of finish transaction done is never executed, neither my onSuccess callback. However the console.log before finishTransaction is logged.

About this issue

  • Original URL
  • State: closed
  • Created 2 years ago
  • Reactions: 7
  • Comments: 41

Most upvoted comments

This seems to be fixed for me in 8.0.5

I ended up just rewriting that function entirely

@objc public func finishTransaction( _ transactionIdentifier: String, resolve: @escaping RCTPromiseResolveBlock = { _ in }, reject: @escaping RCTPromiseRejectBlock = { _, _, _ in } ) { let queue = SKPaymentQueue.default() for transaction in queue.transactions { if transaction.transactionIdentifier == transactionIdentifier { if transaction.transactionState == .purchasing { print("transaction is purchasing still") } else { SKPaymentQueue.default().finishTransaction(transaction) resolve(nil) } } } }

Following the history of the file, it looks like this was broken trying to fix https://github.com/dooboolab/react-native-iap/issues/1637 , by adding the promise methods in the header but not calling resolve/reject. I have fixed both methods (finishTransaction and clearTransaction) here: https://github.com/dooboolab/react-native-iap/pull/1665 Thank you all for helping with the research

@mikeportanova have you tried receipt validation with subscriptions? I’m getting 21199 error response.

I still have the same issue in v8.0.5. @aijcoa Can you please provide more info on how you managed to solve it?

This problem definitely persists in 8.0.5. How are you implementing it., @aijcoa?