cordova-plugin-purchase icon indicating copy to clipboard operation
cordova-plugin-purchase copied to clipboard

iOS - Getting receipts instead of products

Open Clarus2137 opened this issue 1 year ago • 1 comments

I understand that I'm doing something wrong, but I have almost zero understanding of what it is. The problem is as follows. When opening the page where products from my Apple Store Connect should be displayed, the variable from which I planned to read them somehow receives a receipt immediately instead of product data.

Please help me figure this out. The project has been stuck for almost a year because of this issue. I can provide the code if necessary. The template is Vue3 + TypeScript. The project is built with Quasar and Cordova.

P.S.: Product type - consumable

Clarus2137 avatar Jan 22 '25 10:01 Clarus2137

Hi there!

I understand your confusion regarding receiving receipts instead of product data on iOS. This is actually an expected behavior with the plugin due to how the iOS StoreKit works compared to other platforms.

What's happening:

The Cordova Purchase plugin has two different flows happening:

  1. Product Loading: When you initialize the store, it loads product information from Apple's servers.
  2. Receipt Processing: For iOS specifically, the plugin also loads the AppStore receipt which contains information about past purchases.

The issue you're experiencing is that on iOS, the receipt loading often happens before product loading completes. This is particularly noticeable in development/testing when your iOS app is freshly installed.

How to fix this:

You should be using the productUpdated event to know when the products are ready to be displayed. Here's how to properly structure your initialization:

// Define your store setup
const store = CdvPurchase.store;

// Register your products
store.register([{
  id: 'your_product_id',
  type: CdvPurchase.ProductType.CONSUMABLE,
  platform: CdvPurchase.Platform.APPLE_APPSTORE
}]);

// Set up your event listeners BEFORE initializing
store.when()
  .productUpdated(() => {
    // This is called when products are loaded from the store
    console.log('Products loaded:', store.products);
    // Now you can safely access product information
    // Update your UI here
  })
  .receiptsReady(() => {
    // Called when receipts are ready (which may happen earlier on iOS)
    console.log('Receipts ready');
  });

// Initialize the store
store.initialize([{
  platform: CdvPurchase.Platform.APPLE_APPSTORE
}]);

The key points are:

  • Register your event handlers before calling initialize()
  • Only try to access and display products in the productUpdated() callback
  • Don't rely on the initialization completion to access products, as they may not be loaded yet even though receipts are

This works because the productUpdated callback is called specifically when product information is loaded from the Apple AppStore, while the receiptsReady event can happen independently.

Let me know if this helps or if you need further clarification!

j3k0 avatar Mar 07 '25 22:03 j3k0