react-native-iap 11.0.0-rc.2 → 11.0.0-rc.3

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (39) hide show
  1. package/ios/IapSerializationUtils.swift +50 -11
  2. package/ios/IapTypes.swift +1 -6
  3. package/ios/RNIapIos.swift +2 -1
  4. package/ios/RNIapIosSk2.m +2 -1
  5. package/ios/RNIapIosSk2.swift +29 -16
  6. package/lib/commonjs/eventEmitter.js +145 -2
  7. package/lib/commonjs/eventEmitter.js.map +1 -1
  8. package/lib/commonjs/hooks/withIAPContext.js +8 -1
  9. package/lib/commonjs/hooks/withIAPContext.js.map +1 -1
  10. package/lib/commonjs/iap.js +40 -26
  11. package/lib/commonjs/iap.js.map +1 -1
  12. package/lib/commonjs/modules/ios.js +5 -2
  13. package/lib/commonjs/modules/ios.js.map +1 -1
  14. package/lib/commonjs/modules/iosSk2.js.map +1 -1
  15. package/lib/commonjs/types/appleSk2.js +2 -2
  16. package/lib/commonjs/types/appleSk2.js.map +1 -1
  17. package/lib/module/eventEmitter.js +141 -1
  18. package/lib/module/eventEmitter.js.map +1 -1
  19. package/lib/module/hooks/withIAPContext.js +9 -2
  20. package/lib/module/hooks/withIAPContext.js.map +1 -1
  21. package/lib/module/iap.js +40 -26
  22. package/lib/module/iap.js.map +1 -1
  23. package/lib/module/modules/ios.js +5 -2
  24. package/lib/module/modules/ios.js.map +1 -1
  25. package/lib/module/modules/iosSk2.js.map +1 -1
  26. package/lib/module/types/appleSk2.js +2 -2
  27. package/lib/module/types/appleSk2.js.map +1 -1
  28. package/lib/typescript/eventEmitter.d.ts +133 -0
  29. package/lib/typescript/hooks/withIAPContext.d.ts +2 -0
  30. package/lib/typescript/iap.d.ts +10 -2
  31. package/lib/typescript/modules/iosSk2.d.ts +1 -1
  32. package/lib/typescript/types/appleSk2.d.ts +30 -1
  33. package/package.json +1 -1
  34. package/src/eventEmitter.ts +144 -2
  35. package/src/hooks/withIAPContext.tsx +15 -0
  36. package/src/iap.ts +14 -6
  37. package/src/modules/ios.ts +5 -2
  38. package/src/modules/iosSk2.ts +3 -1
  39. package/src/types/appleSk2.ts +40 -3
@@ -1,17 +1,150 @@
1
1
  import { EmitterSubscription } from 'react-native';
2
+ import { TransactionEvent } from './types/appleSk2';
2
3
  import type { PurchaseError } from './purchaseError';
3
4
  import type { Purchase } from './types';
4
5
  /**
5
6
  * Add IAP purchase event
7
+ * Register a callback that gets called when the store has any updates to purchases that have not yet been finished, consumed or acknowledged. Returns a React Native `EmitterSubscription` on which you can call `.remove()` to stop receiving updates. Register you listener as soon as possible and react to updates at all times.
8
+
9
+ ## Signature
10
+
11
+ ```ts
12
+ purchaseUpdatedListener((purchase: Purchase) => {});
13
+ ```
14
+
15
+ ## Usage
16
+
17
+ ```tsx
18
+ import React, {useEffect} from 'react';
19
+ import {View} from 'react-native';
20
+ import {purchaseUpdatedListener} from 'react-native-iap';
21
+
22
+ const App = () => {
23
+ useEffect(() => {
24
+ const subscription = purchaseUpdatedListener((purchase: Purchase) => {
25
+ console.log(purchase);
26
+ });
27
+
28
+ return () => {
29
+ subscription.remove();
30
+ };
31
+ }, []);
32
+
33
+ return <View />;
34
+ };
35
+ ```
6
36
  */
7
37
  export declare const purchaseUpdatedListener: (listener: (event: Purchase) => void) => EmitterSubscription;
8
38
  /**
9
39
  * Add IAP purchase error event
40
+ * Register a callback that gets called when there has been an error with a purchase. Returns a React Native `EmitterSubscription` on which you can call `.remove()` to stop receiving updates.
41
+
42
+ ## Signature
43
+
44
+ ```ts
45
+ purchaseErrorListener((error: PurchaseError) => {});
46
+ ```
47
+
48
+ ## Usage
49
+
50
+ ```tsx
51
+ import React, {useEffect} from 'react';
52
+ import {View} from 'react-native';
53
+ import {purchaseErrorListener} from 'react-native-iap';
54
+
55
+ const App = () => {
56
+ useEffect(() => {
57
+ const subscription = purchaseErrorListener((error: PurchaseError) => {
58
+ console.log(error);
59
+ });
60
+
61
+ return () => {
62
+ subscription.remove();
63
+ };
64
+ }, []);
65
+
66
+ return <View />;
67
+ };
68
+ ```
69
+
10
70
  */
11
71
  export declare const purchaseErrorListener: (listener: (error: PurchaseError) => void) => EmitterSubscription;
12
72
  /**
13
73
  * Add IAP promoted subscription event
74
+ * Add IAP promoted subscription event.
75
+
76
+ ## Signature
77
+
78
+ ```ts
79
+ promotedProductListener((productId?: string) => {});
80
+ ```
81
+
82
+ ## Usage
83
+
84
+ ```tsx
85
+ import React, {useEffect} from 'react';
86
+ import {View} from 'react-native';
87
+ import {promotedProductListener} from 'react-native-iap';
88
+
89
+ const App = () => {
90
+ useEffect(() => {
91
+ const subscription = promotedProductListener((productId) => {
92
+ console.log(productId);
93
+ });
94
+
95
+ return () => {
96
+ subscription.remove();
97
+ };
98
+ }, []);
99
+
100
+ return <View />;
101
+ };
102
+ ```
103
+
14
104
  *
15
105
  * @platform iOS
16
106
  */
17
107
  export declare const promotedProductListener: (listener: () => void) => EmitterSubscription | null;
108
+ /**
109
+ * Updated transactions for iOS Sk2
110
+ * Register a callback that gets called when the store has any updates to transactions related to purchases that have not yet been finished, consumed or acknowledged.
111
+ * Returns a React Native `EmitterSubscription` on which you can call `.remove()` to stop receiving updates. Register you listener as soon as possible and react to updates at all times.
112
+
113
+ **Warning**
114
+ This is only available for iOS 15 and higher and Storekit 2 is activated
115
+
116
+ ## Signature
117
+
118
+ ```ts
119
+ purchaseUpdatedListener((transactionOrError: TransactionOrError) => {});
120
+ ```
121
+
122
+ ## Usage
123
+
124
+ ```tsx
125
+ import React, {useEffect} from 'react';
126
+ import {View} from 'react-native';
127
+ import {purchaseUpdatedListener} from 'react-native-iap';
128
+
129
+ const App = () => {
130
+ useEffect(() => {
131
+ const subscription = purchaseUpdatedListener((transactionOrError: TransactionOrError) => {
132
+ if(transactionOrError.transaction){
133
+ console.log("There's an update to a transaction", transactionOrError.transaction);
134
+ }else{
135
+ console.log("There's been an error with a received transaction")
136
+ }
137
+ });
138
+
139
+ return () => {
140
+ subscription.remove();
141
+ };
142
+ }, []);
143
+
144
+ return <View />;
145
+ };
146
+ ```
147
+ *
148
+ * @platform iOS (Sk2)
149
+ */
150
+ export declare const transactionListener: (listener: (event: TransactionEvent) => void) => EmitterSubscription | null;
@@ -1,6 +1,7 @@
1
1
  import React from 'react';
2
2
  import type { PurchaseError } from '../purchaseError';
3
3
  import type { Product, Purchase, Subscription } from '../types';
4
+ import type { TransactionSk2 } from '../types/appleSk2';
4
5
  declare type IAPContextType = {
5
6
  connected: boolean;
6
7
  products: Product[];
@@ -9,6 +10,7 @@ declare type IAPContextType = {
9
10
  purchaseHistory: Purchase[];
10
11
  availablePurchases: Purchase[];
11
12
  currentPurchase?: Purchase;
13
+ currentTransaction?: TransactionSk2;
12
14
  currentPurchaseError?: PurchaseError;
13
15
  initConnectionError?: Error;
14
16
  setProducts: (products: Product[]) => void;
@@ -143,8 +143,12 @@ const App = () => {
143
143
  return <View />;
144
144
  };
145
145
  ```
146
+ @param {alsoPublishToEventListener}:boolean When `true`, every element will also be pushed to the purchaseUpdated listener.
147
+ Note that this is only for backaward compatiblity. It won't publish to transactionUpdated (Storekit2) Defaults to `false`
146
148
  */
147
- export declare const getPurchaseHistory: () => Promise<(ProductPurchase | SubscriptionPurchase)[]>;
149
+ export declare const getPurchaseHistory: ({ alsoPublishToEventListener, }?: {
150
+ alsoPublishToEventListener?: boolean | undefined;
151
+ }) => Promise<(ProductPurchase | SubscriptionPurchase)[]>;
148
152
  /**
149
153
  * Get all purchases made by the user (either non-consumable, or haven't been consumed yet)
150
154
  * ## Usage
@@ -221,9 +225,13 @@ const App = () => {
221
225
  )
222
226
  };
223
227
  ```
228
+ @param {alsoPublishToEventListener}:boolean When `true`, every element will also be pushed to the purchaseUpdated listener.
229
+ Note that this is only for backaward compatiblity. It won't publish to transactionUpdated (Storekit2) Defaults to `false`
224
230
  *
225
231
  */
226
- export declare const getAvailablePurchases: () => Promise<(ProductPurchase | SubscriptionPurchase)[]>;
232
+ export declare const getAvailablePurchases: ({ alsoPublishToEventListener, }?: {
233
+ alsoPublishToEventListener?: boolean | undefined;
234
+ }) => Promise<(ProductPurchase | SubscriptionPurchase)[]>;
227
235
  /**
228
236
  * Request a purchase for product. This will be received in `PurchaseUpdatedListener`.
229
237
  * Request a purchase for a product (consumables or non-consumables).
@@ -2,7 +2,7 @@ import type { Product, ProductPurchase, Purchase, Sku } from '../types';
2
2
  import type { PaymentDiscountSk2, ProductSk2, ProductStatus, TransactionSk2 } from '../types/appleSk2';
3
3
  import type { NativeModuleProps } from './common';
4
4
  declare type getItems = (skus: Sku[]) => Promise<ProductSk2[]>;
5
- declare type getAvailableItems = () => Promise<Purchase[]>;
5
+ declare type getAvailableItems = (alsoPublishToEventListener?: boolean) => Promise<Purchase[]>;
6
6
  export declare type BuyProduct = (sku: Sku, andDangerouslyFinishTransactionAutomaticallyIOS: boolean, applicationUsername: string | undefined, quantity: number, withOffer: PaymentDiscountSk2 | undefined) => Promise<Purchase>;
7
7
  declare type clearTransaction = () => Promise<void>;
8
8
  declare type clearProducts = () => Promise<void>;
@@ -1,5 +1,26 @@
1
+ import type { PurchaseError } from '../purchaseError';
1
2
  import type { ProductIOS, Purchase, SubscriptionIOS } from '.';
2
3
  import type * as Apple from './apple';
4
+ export declare type SubscriptionPeriod = {
5
+ unit: 'day' | 'week' | 'month' | 'year';
6
+ value: number;
7
+ };
8
+ export declare type PaymentMode = 'freeTrial' | 'payAsYouGo' | 'payUpFront';
9
+ export declare type SubscriptionOffer = {
10
+ displayPrice: string;
11
+ id: string;
12
+ paymentMode: PaymentMode;
13
+ period: SubscriptionPeriod;
14
+ periodCount: number;
15
+ price: number;
16
+ type: 'introductory' | 'promotional';
17
+ };
18
+ export declare type SubscriptionInfo = {
19
+ introductoryOffer?: SubscriptionOffer;
20
+ promotionalOffers?: SubscriptionOffer[];
21
+ subscriptionGroupID: string;
22
+ subscriptionPeriod: SubscriptionPeriod;
23
+ };
3
24
  export declare type ProductSk2 = {
4
25
  description: string;
5
26
  displayName: string;
@@ -8,7 +29,7 @@ export declare type ProductSk2 = {
8
29
  isFamilyShareable: boolean;
9
30
  jsonRepresentation: string;
10
31
  price: number;
11
- subscription: any;
32
+ subscription: SubscriptionInfo;
12
33
  type: 'autoRenewable' | 'consumable' | 'nonConsumable' | 'nonRenewable';
13
34
  };
14
35
  export declare const productSk2Map: ({ id, description, displayName, price, displayPrice, }: ProductSk2) => ProductIOS;
@@ -38,6 +59,14 @@ export declare type TransactionSk2 = {
38
59
  subscriptionGroupID: number;
39
60
  webOrderLineItemID: number;
40
61
  };
62
+ export declare type TransactionError = PurchaseError;
63
+ /**
64
+ * Only one of `transaction` and `error` is not undefined at the time
65
+ */
66
+ export declare type TransactionEvent = {
67
+ transaction?: TransactionSk2;
68
+ error?: TransactionError;
69
+ };
41
70
  export declare type SubscriptionStatus = 'expired' | 'inBillingRetryPeriod' | 'inGracePeriod' | 'revoked' | 'subscribed';
42
71
  export declare type ProductStatus = {
43
72
  state: SubscriptionStatus;
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "react-native-iap",
3
- "version": "11.0.0-rc.2",
3
+ "version": "11.0.0-rc.3",
4
4
  "description": "React Native In App Purchase Module.",
5
5
  "repository": "https://github.com/dooboolab/react-native-iap",
6
6
  "author": "dooboolab <support@dooboolab.com> (https://github.com/dooboolab)",
@@ -1,6 +1,6 @@
1
1
  import {EmitterSubscription, NativeEventEmitter} from 'react-native';
2
2
 
3
- import {transactionSk2Map} from './types/appleSk2';
3
+ import {TransactionEvent, transactionSk2Map} from './types/appleSk2';
4
4
  import {isIosStorekit2} from './iap';
5
5
  import {
6
6
  getAndroidModule,
@@ -14,6 +14,35 @@ import type {Purchase} from './types';
14
14
 
15
15
  /**
16
16
  * Add IAP purchase event
17
+ * Register a callback that gets called when the store has any updates to purchases that have not yet been finished, consumed or acknowledged. Returns a React Native `EmitterSubscription` on which you can call `.remove()` to stop receiving updates. Register you listener as soon as possible and react to updates at all times.
18
+
19
+ ## Signature
20
+
21
+ ```ts
22
+ purchaseUpdatedListener((purchase: Purchase) => {});
23
+ ```
24
+
25
+ ## Usage
26
+
27
+ ```tsx
28
+ import React, {useEffect} from 'react';
29
+ import {View} from 'react-native';
30
+ import {purchaseUpdatedListener} from 'react-native-iap';
31
+
32
+ const App = () => {
33
+ useEffect(() => {
34
+ const subscription = purchaseUpdatedListener((purchase: Purchase) => {
35
+ console.log(purchase);
36
+ });
37
+
38
+ return () => {
39
+ subscription.remove();
40
+ };
41
+ }, []);
42
+
43
+ return <View />;
44
+ };
45
+ ```
17
46
  */
18
47
  export const purchaseUpdatedListener = (
19
48
  listener: (event: Purchase) => void,
@@ -38,6 +67,36 @@ export const purchaseUpdatedListener = (
38
67
 
39
68
  /**
40
69
  * Add IAP purchase error event
70
+ * Register a callback that gets called when there has been an error with a purchase. Returns a React Native `EmitterSubscription` on which you can call `.remove()` to stop receiving updates.
71
+
72
+ ## Signature
73
+
74
+ ```ts
75
+ purchaseErrorListener((error: PurchaseError) => {});
76
+ ```
77
+
78
+ ## Usage
79
+
80
+ ```tsx
81
+ import React, {useEffect} from 'react';
82
+ import {View} from 'react-native';
83
+ import {purchaseErrorListener} from 'react-native-iap';
84
+
85
+ const App = () => {
86
+ useEffect(() => {
87
+ const subscription = purchaseErrorListener((error: PurchaseError) => {
88
+ console.log(error);
89
+ });
90
+
91
+ return () => {
92
+ subscription.remove();
93
+ };
94
+ }, []);
95
+
96
+ return <View />;
97
+ };
98
+ ```
99
+
41
100
  */
42
101
  export const purchaseErrorListener = (
43
102
  listener: (error: PurchaseError) => void,
@@ -48,14 +107,97 @@ export const purchaseErrorListener = (
48
107
 
49
108
  /**
50
109
  * Add IAP promoted subscription event
110
+ * Add IAP promoted subscription event.
111
+
112
+ ## Signature
113
+
114
+ ```ts
115
+ promotedProductListener((productId?: string) => {});
116
+ ```
117
+
118
+ ## Usage
119
+
120
+ ```tsx
121
+ import React, {useEffect} from 'react';
122
+ import {View} from 'react-native';
123
+ import {promotedProductListener} from 'react-native-iap';
124
+
125
+ const App = () => {
126
+ useEffect(() => {
127
+ const subscription = promotedProductListener((productId) => {
128
+ console.log(productId);
129
+ });
130
+
131
+ return () => {
132
+ subscription.remove();
133
+ };
134
+ }, []);
135
+
136
+ return <View />;
137
+ };
138
+ ```
139
+
51
140
  *
52
141
  * @platform iOS
53
142
  */
54
143
  export const promotedProductListener = (listener: () => void) => {
55
- if (isIos) {
144
+ if (isIos && !isIosStorekit2()) {
56
145
  const eventEmitter = new NativeEventEmitter(getIosModule());
57
146
  return eventEmitter.addListener('iap-promoted-product', listener);
58
147
  }
59
148
 
60
149
  return null;
61
150
  };
151
+
152
+ /**
153
+ * Updated transactions for iOS Sk2
154
+ * Register a callback that gets called when the store has any updates to transactions related to purchases that have not yet been finished, consumed or acknowledged.
155
+ * Returns a React Native `EmitterSubscription` on which you can call `.remove()` to stop receiving updates. Register you listener as soon as possible and react to updates at all times.
156
+
157
+ **Warning**
158
+ This is only available for iOS 15 and higher and Storekit 2 is activated
159
+
160
+ ## Signature
161
+
162
+ ```ts
163
+ purchaseUpdatedListener((transactionOrError: TransactionOrError) => {});
164
+ ```
165
+
166
+ ## Usage
167
+
168
+ ```tsx
169
+ import React, {useEffect} from 'react';
170
+ import {View} from 'react-native';
171
+ import {purchaseUpdatedListener} from 'react-native-iap';
172
+
173
+ const App = () => {
174
+ useEffect(() => {
175
+ const subscription = purchaseUpdatedListener((transactionOrError: TransactionOrError) => {
176
+ if(transactionOrError.transaction){
177
+ console.log("There's an update to a transaction", transactionOrError.transaction);
178
+ }else{
179
+ console.log("There's been an error with a received transaction")
180
+ }
181
+ });
182
+
183
+ return () => {
184
+ subscription.remove();
185
+ };
186
+ }, []);
187
+
188
+ return <View />;
189
+ };
190
+ ```
191
+ *
192
+ * @platform iOS (Sk2)
193
+ */
194
+ export const transactionListener = (
195
+ listener: (event: TransactionEvent) => void,
196
+ ) => {
197
+ if (isIos && isIosStorekit2()) {
198
+ const eventEmitter = new NativeEventEmitter(getIosModule());
199
+ return eventEmitter.addListener('iap-transaction-updated', listener);
200
+ }
201
+
202
+ return null;
203
+ };
@@ -4,6 +4,7 @@ import {
4
4
  promotedProductListener,
5
5
  purchaseErrorListener,
6
6
  purchaseUpdatedListener,
7
+ transactionListener,
7
8
  } from '../eventEmitter';
8
9
  import {IapIos, initConnection} from '../iap';
9
10
  import type {PurchaseError} from '../purchaseError';
@@ -14,6 +15,7 @@ import type {
14
15
  Subscription,
15
16
  SubscriptionPurchase,
16
17
  } from '../types';
18
+ import type {TransactionEvent, TransactionSk2} from '../types/appleSk2';
17
19
 
18
20
  type IAPContextType = {
19
21
  connected: boolean;
@@ -23,6 +25,7 @@ type IAPContextType = {
23
25
  purchaseHistory: Purchase[];
24
26
  availablePurchases: Purchase[];
25
27
  currentPurchase?: Purchase;
28
+ currentTransaction?: TransactionSk2;
26
29
  currentPurchaseError?: PurchaseError;
27
30
  initConnectionError?: Error;
28
31
  setProducts: (products: Product[]) => void;
@@ -63,6 +66,8 @@ export function withIAPContext<T>(Component: React.ComponentType<T>) {
63
66
  [],
64
67
  );
65
68
  const [currentPurchase, setCurrentPurchase] = useState<Purchase>();
69
+ const [currentTransaction, setCurrentTransaction] =
70
+ useState<TransactionSk2>();
66
71
 
67
72
  const [currentPurchaseError, setCurrentPurchaseError] =
68
73
  useState<PurchaseError>();
@@ -78,6 +83,7 @@ export function withIAPContext<T>(Component: React.ComponentType<T>) {
78
83
  purchaseHistory,
79
84
  availablePurchases,
80
85
  currentPurchase,
86
+ currentTransaction,
81
87
  currentPurchaseError,
82
88
  initConnectionError,
83
89
  setProducts,
@@ -95,6 +101,7 @@ export function withIAPContext<T>(Component: React.ComponentType<T>) {
95
101
  purchaseHistory,
96
102
  availablePurchases,
97
103
  currentPurchase,
104
+ currentTransaction,
98
105
  currentPurchaseError,
99
106
  initConnectionError,
100
107
  setProducts,
@@ -127,6 +134,13 @@ export function withIAPContext<T>(Component: React.ComponentType<T>) {
127
134
  },
128
135
  );
129
136
 
137
+ const transactionUpdateSubscription = transactionListener(
138
+ async (transactionOrError: TransactionEvent) => {
139
+ setCurrentPurchaseError(transactionOrError?.error);
140
+ setCurrentTransaction(transactionOrError?.transaction);
141
+ },
142
+ );
143
+
130
144
  const purchaseErrorSubscription = purchaseErrorListener(
131
145
  (error: PurchaseError) => {
132
146
  setCurrentPurchase(undefined);
@@ -147,6 +161,7 @@ export function withIAPContext<T>(Component: React.ComponentType<T>) {
147
161
  purchaseUpdateSubscription.remove();
148
162
  purchaseErrorSubscription.remove();
149
163
  promotedProductSubscription?.remove();
164
+ transactionUpdateSubscription?.remove();
150
165
  };
151
166
  }, [connected]);
152
167
 
package/src/iap.ts CHANGED
@@ -248,14 +248,18 @@ const App = () => {
248
248
  return <View />;
249
249
  };
250
250
  ```
251
+ @param {alsoPublishToEventListener}:boolean When `true`, every element will also be pushed to the purchaseUpdated listener.
252
+ Note that this is only for backaward compatiblity. It won't publish to transactionUpdated (Storekit2) Defaults to `false`
251
253
  */
252
- export const getPurchaseHistory = (): Promise<
253
- (ProductPurchase | SubscriptionPurchase)[]
254
- > =>
254
+ export const getPurchaseHistory = ({
255
+ alsoPublishToEventListener = false,
256
+ }: {
257
+ alsoPublishToEventListener?: boolean;
258
+ } = {}): Promise<(ProductPurchase | SubscriptionPurchase)[]> =>
255
259
  (
256
260
  Platform.select({
257
261
  ios: async () => {
258
- return getIosModule().getAvailableItems();
262
+ return getIosModule().getAvailableItems(alsoPublishToEventListener);
259
263
  },
260
264
  android: async () => {
261
265
  if (RNIapAmazonModule) {
@@ -351,15 +355,19 @@ const App = () => {
351
355
  )
352
356
  };
353
357
  ```
358
+ @param {alsoPublishToEventListener}:boolean When `true`, every element will also be pushed to the purchaseUpdated listener.
359
+ Note that this is only for backaward compatiblity. It won't publish to transactionUpdated (Storekit2) Defaults to `false`
354
360
  *
355
361
  */
356
- export const getAvailablePurchases = (): Promise<
362
+ export const getAvailablePurchases = ({
363
+ alsoPublishToEventListener = false,
364
+ }: {alsoPublishToEventListener?: boolean} = {}): Promise<
357
365
  (ProductPurchase | SubscriptionPurchase)[]
358
366
  > =>
359
367
  (
360
368
  Platform.select({
361
369
  ios: async () => {
362
- return getIosModule().getAvailableItems();
370
+ return getIosModule().getAvailableItems(alsoPublishToEventListener);
363
371
  },
364
372
  android: async () => {
365
373
  if (RNIapAmazonModule) {
@@ -84,7 +84,7 @@ export const getPromotedProductIOS = (): Promise<Product | null> => {
84
84
  if (!isIosStorekit2()) {
85
85
  return getIosModule().promotedProduct();
86
86
  } else {
87
- return Promise.reject('Only available on SK1');
87
+ return Promise.reject('Only available on Sk1');
88
88
  }
89
89
  };
90
90
 
@@ -146,7 +146,10 @@ export const validateReceiptIos = async ({
146
146
  ? 'https://sandbox.itunes.apple.com/verifyReceipt'
147
147
  : 'https://buy.itunes.apple.com/verifyReceipt';
148
148
 
149
- return await enhancedFetch<ReceiptValidationResponse>(url);
149
+ return await enhancedFetch<ReceiptValidationResponse>(url, {
150
+ method: 'POST',
151
+ body: receiptBody,
152
+ });
150
153
  };
151
154
 
152
155
  /**
@@ -13,7 +13,9 @@ const {RNIapIosSk2} = NativeModules;
13
13
 
14
14
  type getItems = (skus: Sku[]) => Promise<ProductSk2[]>;
15
15
 
16
- type getAvailableItems = () => Promise<Purchase[]>;
16
+ type getAvailableItems = (
17
+ alsoPublishToEventListener?: boolean,
18
+ ) => Promise<Purchase[]>;
17
19
 
18
20
  export type BuyProduct = (
19
21
  sku: Sku,
@@ -1,5 +1,32 @@
1
+ import type {PurchaseError} from '../purchaseError';
2
+
1
3
  import type {ProductIOS, Purchase, SubscriptionIOS} from '.';
2
4
  import type * as Apple from './apple';
5
+
6
+ export type SubscriptionPeriod = {
7
+ unit: 'day' | 'week' | 'month' | 'year';
8
+ value: number;
9
+ };
10
+
11
+ export type PaymentMode = 'freeTrial' | 'payAsYouGo' | 'payUpFront';
12
+
13
+ export type SubscriptionOffer = {
14
+ displayPrice: string;
15
+ id: string;
16
+ paymentMode: PaymentMode;
17
+ period: SubscriptionPeriod;
18
+ periodCount: number;
19
+ price: number;
20
+ type: 'introductory' | 'promotional';
21
+ };
22
+
23
+ export type SubscriptionInfo = {
24
+ introductoryOffer?: SubscriptionOffer;
25
+ promotionalOffers?: SubscriptionOffer[];
26
+ subscriptionGroupID: string;
27
+ subscriptionPeriod: SubscriptionPeriod;
28
+ };
29
+
3
30
  export type ProductSk2 = {
4
31
  description: string;
5
32
  displayName: string;
@@ -8,7 +35,7 @@ export type ProductSk2 = {
8
35
  isFamilyShareable: boolean;
9
36
  jsonRepresentation: string;
10
37
  price: number;
11
- subscription: any; //TODO
38
+ subscription: SubscriptionInfo;
12
39
  type: 'autoRenewable' | 'consumable' | 'nonConsumable' | 'nonRenewable';
13
40
  };
14
41
  export const productSk2Map = ({
@@ -25,7 +52,7 @@ export const productSk2Map = ({
25
52
  type: 'iap',
26
53
  price: String(price),
27
54
  localizedPrice: displayPrice,
28
- currency: '', //TODO: Not avaiable on new API, use localizedPrice instead?
55
+ currency: '', // Not avaiable on new API, use localizedPrice instead
29
56
  };
30
57
  return prod;
31
58
  };
@@ -44,7 +71,7 @@ export const subscriptionSk2Map = ({
44
71
  type: 'subs',
45
72
  price: String(price),
46
73
  localizedPrice: displayPrice,
47
- currency: '', //TODO: Not avaiable on new API, use localizedPrice instead?
74
+ currency: '', // Not avaiable on new API, use localizedPrice instead
48
75
  };
49
76
  return prod;
50
77
  };
@@ -75,6 +102,16 @@ export type TransactionSk2 = {
75
102
  webOrderLineItemID: number;
76
103
  };
77
104
 
105
+ export type TransactionError = PurchaseError;
106
+
107
+ /**
108
+ * Only one of `transaction` and `error` is not undefined at the time
109
+ */
110
+ export type TransactionEvent = {
111
+ transaction?: TransactionSk2;
112
+ error?: TransactionError;
113
+ };
114
+
78
115
  export type SubscriptionStatus =
79
116
  | 'expired'
80
117
  | 'inBillingRetryPeriod'