Ata
Ata

Reputation: 27

Error: Stripe: Argument "intent" must be a string, but got: undefined

I'm trying to integrate the stripe payment gateway to my event application. I'm currently only implementing the server side, and the code below is the attend to the event functionality in the userController.js script, which should, upon clicking on the register to the event button, redirect the user to the checkout page, where the user enters his/her card details. Once the payment is completed, the user should be added to the attendees list and so on. However, I encounter an error that I'm unable to solve. I'm just trying to learn node by learning by doing, so any help would be really appreciated!

Code:

// @desc    Register to an event
// @route   POST /api/events/attend
// @access  Private
const attendToEvent = asyncHandler(async (req, res) => {
  const {eventID} = req.body
  const paymentSuccessful = false


  // Check for event
  validEventID = mongoose.Types.ObjectId.isValid({eventID});


  const event = await Event.findOne({_id:eventID})
  const user = req.user

  if (event == null) {
    res.status(400)
    throw new Error('Invalid Event id.')
  }



  registered = await User.findOne({attendsTo: event._id})
  console.log(`user registered: ${registered}`)
  
  if (registered != null) {
    res.status(400)
    throw new Error('You are already registered to this event.')
  }
  var customer = await stripe.customers.create({
    name: user.username,
    email: user.email,
    source: req.body.stripeToken
  })
  const paymentMethods = await stripe.paymentMethods.list({
    customer: customer.id,
    type: 'card',
  });

  //Get create customer on stripe and get the payment
  stripe.paymentIntents.create({
    amount:1000,
    currency: 'usd',
    customer: customer.id,
    payment_method: paymentMethods.id
  }).then(function(confirm) {
    return stripe.paymentIntents.confirm(
      paymentMethods.id,
      {payment_method: 'pm_card_visa'}
    )
  }).then(function(result) {
    if (result.error) {
      return console.log('Payment unsuccessful')
      
    } else {
      paymentSuccessful = true
      return paymentSuccessful
    }
  })
  
  if (!registered && paymentSuccessful) {
    User.findOneAndUpdate(
      { _id: user._id }, 
      { $push: { attendsTo: event._id  } },
     function (error, success) {
           if (error) {
               console.log(error);
           } else {
               console.log(success);
           }
       });
    
    Event.findOneAndUpdate(
      {_id: event._id},
      {$push: {attendees: user._id}},
      function (error, success) {
        if (error) {
          console.log(error);
        }
        else {
          console.log(success);
        }
      }
    );
    //res.render("../completed.html")
    res.status(201).send(`Successfully registered to event: ${event.eventname}`)
  }
})

Error:

Error: Stripe: Argument "intent" must be a string, but got: undefined (on API request to `POST /payment_intents/{intent}/confirm`)

Upvotes: 0

Views: 1808

Answers (1)

orakaro
orakaro

Reputation: 1971

In your PaymentIntent confirmation call, you are incorrectly passing in a PaymentMethod Id instead of a PaymentIntent Id

}).then(function(confirm) {
  return stripe.paymentIntents.confirm(
    paymentMethods.id, // <--- Here
    {payment_method: 'pm_card_visa'}
  )
})

Look at Stripe's Doc, you will see the Id should be in format of pi_xxx, which is a Payment Intent Id format. In this case it should be confirm.id.

Upvotes: 1

Related Questions