简体   繁体   中英

Error creating a payment intent for Stripe with Firebase in NodeJS

I'm attempting to create a Stripe payment intent in NodeJS with Firebase. Server function receives JSON from my iOS app, retrieves the product correctly and gets the product's price (which is confirmed by the correct values in console), but at the very last step it doesn't pass the price value correctly.

Here's the error I receive in my Firebase console:

Error: Invalid integer: {:domain=>{:domain=>"", :_eventsCount=>"1"}}
    at Function.generate (/srv/node_modules/stripe/lib/Error.js:38:16)
    at IncomingMessage.res.once (/srv/node_modules/stripe/lib/StripeResource.js:175:33)
    at Object.onceWrapper (events.js:313:30)
    at emitNone (events.js:111:20)
    at IncomingMessage.emit (events.js:208:7)
    at endReadableNT (_stream_readable.js:1064:12)
    at _combinedTickCallback (internal/process/next_tick.js:139:11)
    at process._tickDomainCallback (internal/process/next_tick.js:219:9)

And here's the code:

// New Stripe Payment Intent
const newPaymentIntent = express();
newPaymentIntent.use(bodyParser.urlencoded({ extended: true }));
newPaymentIntent.post('/', (req, res) => { createPaymentIntent(req, res); });
function paymentIntent(req, res) { }
exports.paymentIntent = functions.https.onRequest(newPaymentIntent);

const calculateOrderAmount = items => {
    let price = admin.database().ref('/productAds').orderByChild('code').equalTo(items['code']).once('value').then((snapshot) => {
            var productPrice = 99;

            snapshot.forEach((childSnapshot) => {
          var childData = childSnapshot.val();

                productPrice += childData.price;
                console.log(childData.price);
        });

            console.log(productPrice);
            return productPrice;
    });

    return price;
};

// Create Stripe Customer
async function createPaymentIntent(req, res) {
  const { items, currency } = req.body;

    const paymentIntent = await stripe.paymentIntents.create({
      amount: calculateOrderAmount(items),
      currency: 'aud',
    });
    const clientSecret = paymentIntent.client_secret

    // Send publishable key and PaymentIntent details to client
  res.send({
    publishableKey: 'pk_test_ikLVo1vJSDi89gcfwMiBTDDw',
    clientSecret: clientSecret
  });
}

Any suggestions on what I am doing wrong?

Your function calculateOrderAmount doesn't return a number. It returns a promise that will resolve with the value returned by the function you passed to then .

You should use another then to wait for the final value, and only then invoke the stripe API. Or use async. (If you have the capability of using async, you should probably also use it in your calculateOrderAmount function instead of using then , as it will be easier to read and reason about.)

So Doug was correct. I edited the code to include async functions and it works flawlessly now. Here's what the final code looks like:

 // Retrieve product code from Firebase async function getDataFromFirebase(items) { const objects = await admin.database().ref('/productAds').orderByChild('code').equalTo(items['code']) const data = await objects.once('value'); return data; } async function getPrice(items) { console.log('Executing getPrice method.'); var resultPrice = 0; // we wait for the axios.get Promise to be resolved const objects = await getDataFromFirebase(items); objects.forEach((childSnapshot) => { var childData = childSnapshot.val(); resultPrice += childData.price; }); console.log('Price is: ' + resultPrice); // we then return the data, just like we did in the callback-based version; return resultPrice, } // Create Stripe Customer async function createPaymentIntent(req, res) { const { items. currency } = req;body. const paymentIntent = await stripe.paymentIntents:create({ amount, await getPrice(items): currency, 'aud'; }). const clientSecret = paymentIntent.client_secret // Send publishable key and PaymentIntent details to client res:send({ publishableKey, 'pk_test_ikLVo1vJSDi89gcfwMiBTDDw': clientSecret; clientSecret }); }

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