简体   繁体   中英

Firebase extension: Run Subscription Payments with Stripe doesn't return a sessionId

I have installed the "Run Subscription Payments with Stripe" extension in Firebase.

When I try the to subscribe a user to a plan I get an error saying "snap.data is not a function". I use the following code:

 db
      .collection('customers')
      .doc(cred.user.uid)
      .collection('checkout_sessions')
      .add({
        price: 'price_1GqIC8HYgolSBA35zoTTN2Zl',
        success_url: window.location.origin,
        cancel_url: window.location.origin,
      }).then(() => {
    // Wait for the CheckoutSession to get attached by the extension
      db
      .collection('customers')
      .doc(cred.user.uid)
      .collection('checkout_sessions').onSnapshot((snap) => {

          console.log(snap)

          const { sessionId } = snap.data();
          if ({sessionId}) {

            console.log(sessionId)
            // We have a session, let's redirect to Checkout
            // Init Stripe
            const stripe = Stripe('pk_test_ZEgiqIsOgob2wWIceTh0kCV4001CPznHi4');
            stripe.redirectToCheckout({ sessionId });
          };
    });
  });

This is a .then variation on the code example provided by the Firebase team:

const docRef = await db
  .collection('customers')
  .doc(currentUser.uid)
  .collection('checkout_sessions')
  .add({
    price: 'price_1GqIC8HYgolSBA35zoTTN2Zl',
    success_url: window.location.origin,
    cancel_url: window.location.origin,
  });
// Wait for the CheckoutSession to get attached by the extension
docRef.onSnapshot((snap) => {
  const { sessionId } = snap.data();
  if (sessionId) {
    // We have a session, let's redirect to Checkout
    // Init Stripe
    const stripe = Stripe('pk_test_1234');
    stripe.redirectToCheckout({ sessionId });
  }
});

I got an error with the await function, saying "Uncaught SyntaxError: await is only valid in async function". So I refactered the code to a .then variant.

When I run this code from a button.addEventListener("click) I get an error saying snap.data is not a function.

I checked snap and it is populated

console.log() 的快照

The customer gets created in Firestore and in Stripe dashboard, the customer session gets created.

What goes wrong here? There is a similair question on Stackoveflow ( Run Subscription Payments with Stripe Firebase Extension Webhook Not Firing ), but there is no answer, so I'm trying again.

Your query:

  db
      .collection('customers')
      .doc(cred.user.uid)
      .collection('checkout_sessions')

can fetch possibly multiple documents at once. The object it yields is a QuerySnapshot type object that can contain zero or more documents in the results et. That's what your snap is here - a QuerySnapshot . You'll notice that it doesn't have a data() method. That's for DocumentSnapshot objects, where you know you either have a single document or not.

If you have a QuerySnapshot, you'll have to iterate it to get all possible document snapshots out of it, as illustrated in the documentation .

But it seems that's not even what you want to do. It looks like you want to access the document that was previously added using add() . If that's what you want, you shouldn't be querying the entire collection as you are now. Just locate the single document you want and add a listener to it .

You need to listen to updates to the specific document that you juts added via the .add() function. This function returns a reference to that specific document: https://github.com/stripe/stripe-firebase-extensions/blob/next/firestore-stripe-subscriptions/POSTINSTALL.md#start-a-subscription-with-stripe-checkout

If you don't want to / can't use async/await syntax you will need to get that document reference from the .then() function: https://firebase.google.com/docs/firestore/manage-data/add-data#web_6

db.collection("customers")
  .doc(user)
  .collection("checkout_sessions")
  .add({
    price: "price_1I42zfKct2IqsPff6b6vFNKx",
    success_url: window.location.origin,
    cancel_url: window.location.origin,
  })
  .then((docRef) => {
    docRef.onSnapshot((snap) => {
      const { sessionId } = snap.data();
      if ({ sessionId }) {
        console.log(sessionId);
        // We have a session, let's redirect to Checkout
        // Init Stripe
        const stripe = Stripe("pk_test_ZEgiqIsOgob2wWIceTh0kCV4001CPznHi4");
        stripe.redirectToCheckout({ sessionId });
      }
    });
  });

I don't know if this has been resolved. I had a similar issue and changed tsconfig.jason

 "compilerOptions": {
 ...
    "strict": false,
...
}

That did it for me.

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM