React-native-iap: purchaseUpdatedListener wird wiederholt aufgerufen

Erstellt am 3. Feb. 2020  ·  6Kommentare  ·  Quelle: dooboolab/react-native-iap

Version von react-native-iap

4.3.0

Version von React-Native

0,60,5

Plattformen, auf denen Sie den Fehler hatten (IOS oder Android oder beides?)

Beide

Erwartetes Verhalten

Nach dem Beispiel möchte ich nach dem Kauf meines Abonnements eine benutzerdefinierte Methode aufrufen. Nach meinem Verständnis sollte der Hörer nach Bestätigung des Kaufs entfernt werden? Ich habe versucht, remove explizit aufzurufen, hatte aber keinen Erfolg.

Beispiel

 const purchaseListener = purchaseUpdatedListener(purchase => {
      const receipt = purchase.transactionReceipt;
      if (receipt) {
        callCustomEndpoint().then(result => {
          if(result){
            // Subscription is valid
            finishTransaction(purchase);
          }
        }) 
      };
      finishTransaction(purchase);
    });

Tatsächliches Verhalten

Die callCustomEndpoint () -Methode wird mehrmals aufgerufen. Wie kann ich das verhindern? Da ich diesen Endpunkt nur einmal treffen muss.

Ich verwende eine Funktionskomponente anstelle einer Klassenkomponente, wenn dies wichtig ist.

Getestete Umgebung (Emulator? Reales Gerät?)

Echtes Gerät

Schritte zum Reproduzieren des Verhaltens

🙏 help wanted

Hilfreichster Kommentar

Ich werde meine Lösung für Haken für diejenigen aufstellen, die sie später brauchen werden.

außerhalb Ihrer Statuskomponente (obwohl wahrscheinlich auch innerhalb):

var purchaseUpdateSubscription;
var purchaseErrorSubscription;
const loadIAPListeners = () => {
  initConnection(); // important, or else it won't trigger before a random state change
  purchaseUpdateSubscription = purchaseUpdatedListener(
    async (
      purchase: InAppPurchase | SubscriptionPurchase | ProductPurchase,
    ) => {
      console.log('purchaseUpdatedListener', purchase);
      let receipt = purchase.transactionReceipt;
      if (receipt) {
        apis.checkreceipt({data: purchase, platform: Platform.OS}); // I personally don't care about callback
        if (Platform.OS === 'ios') {
          await RNIap.finishTransactionIOS(purchase.transactionId);
        } else if (Platform.OS === 'android') {
          await RNIap.acknowledgePurchaseAndroid(purchase.purchaseToken);
        }
        await RNIap.finishTransaction(purchase, true);
        await RNIap.finishTransaction(purchase, false);
      } else {
        // Retry / conclude the purchase is fraudulent, etc...
      }
    },
  );
  purchaseErrorSubscription = purchaseErrorListener((error: PurchaseError) => {
    console.log('purchaseErrorListener', error);
  });
};

innerhalb Ihrer staatlichen Komponente:

useEffect(() => {
    loadIAPListeners();
    return () => {
      purchaseUpdateSubscription.remove();
      purchaseErrorSubscription.remove();
    };
  }, []);

Alle 6 Kommentare

Ich vermute, Sie haben purchaseListener beim erneuten Rendern von Komponenten mehrmals registriert.

Danke, ich habe dies seitdem mit Hooks umgeschrieben, damit es nicht bei jedem Render aufgerufen wird. Mein Fehler bestand darin, das bereitgestellte Beispiel in den Dokumenten einer Klassenkomponente auf eine Funktionskomponente zu portieren. Tolle Arbeit an der Bibliothek!

@cgathergood Ich habe auch dieses Problem. Haben Sie etwas dagegen, Ihren Event-Handler-Code mithilfe von React-Hooks zu veröffentlichen?

@cgathergood Ich würde gerne auch ein Codebeispiel sehen. Ich kämpfe ein bisschen mit Haken.

@ wootwoot1234 @osmantuna Können Sie bitte die Ereignishandlercodes Problem zu beheben?

Ich werde meine Lösung für Haken für diejenigen aufstellen, die sie später brauchen werden.

außerhalb Ihrer Statuskomponente (obwohl wahrscheinlich auch innerhalb):

var purchaseUpdateSubscription;
var purchaseErrorSubscription;
const loadIAPListeners = () => {
  initConnection(); // important, or else it won't trigger before a random state change
  purchaseUpdateSubscription = purchaseUpdatedListener(
    async (
      purchase: InAppPurchase | SubscriptionPurchase | ProductPurchase,
    ) => {
      console.log('purchaseUpdatedListener', purchase);
      let receipt = purchase.transactionReceipt;
      if (receipt) {
        apis.checkreceipt({data: purchase, platform: Platform.OS}); // I personally don't care about callback
        if (Platform.OS === 'ios') {
          await RNIap.finishTransactionIOS(purchase.transactionId);
        } else if (Platform.OS === 'android') {
          await RNIap.acknowledgePurchaseAndroid(purchase.purchaseToken);
        }
        await RNIap.finishTransaction(purchase, true);
        await RNIap.finishTransaction(purchase, false);
      } else {
        // Retry / conclude the purchase is fraudulent, etc...
      }
    },
  );
  purchaseErrorSubscription = purchaseErrorListener((error: PurchaseError) => {
    console.log('purchaseErrorListener', error);
  });
};

innerhalb Ihrer staatlichen Komponente:

useEffect(() => {
    loadIAPListeners();
    return () => {
      purchaseUpdateSubscription.remove();
      purchaseErrorSubscription.remove();
    };
  }, []);
War diese Seite hilfreich?
0 / 5 - 0 Bewertungen