#rohailkamran

1 messages · Page 1 of 1 (latest)

valid martenBOT
#

Hello! We'll be with you shortly. Below are links to other discussions we've had with you in the past week in case you want to review that information. If your question is related to one of these previous discussions, please provide a comprehensive summary of the current state and what you need help with now. We help many users simultaneously, so a summary allows us to resolve your issue as soon as possible.

bright pulsar
#

Hi, let me help you with this.

#

Are you building a new Stripe integration?

slender zodiac
#

Thanks! And yes.

bright pulsar
#

I strongly recommend against using Charges and Sources API since it's legacy.
And even more, you should absolutely never save credit card info in metadata, since it breaks PCI-compliance: https://stripe.com/gb/guides/pci-compliance

#

What guides are you following?

slender zodiac
#

I see! I would do away with the meta data part immediately.

I have been following the docs here:
https://stripe.com/docs/api

If I should not use charges, what should I use? Payment Intents?

slender zodiac
#

If I use payment intents, my step 2 should look something like this:

const paymentIntent = await stripe.paymentIntents.create({
  amount: 2000,
  currency: 'usd',
  automatic_payment_methods: {
    enabled: true,
  },
  customer: customerId,
});

Thanks. I feel a lot better using things that are actively supported.

Let me try this and get back to you. Do you think this will solve my problem?

bright pulsar
#

Depends what are you trying to do exactly.

slender zodiac
slender zodiac
bright pulsar
slender zodiac
#

I am only trying to do a poc for the following user story:

  1. User goes to a sign up form and optionally puts in their payment details

  2. The payment details go to stripe and a customer id is returned

  3. We create a user in our db with returned customer id with the intention of ideally not having to use anything other than this customer id in the future for payments etc.

  4. Customer goes to dashboard and decides pay for something (a product, subscription, donation whatever)

  5. We simply get the customer id from our db, and use the stripe api to charge the customer the amount for whatever they chose in step 4

Here, steps 1, 2, 3 work, I have also been able to unit test charges and they have worked in test mode.

But doing steps 1, 2, 3, 4, 5 in sequence for a poc has resulted in the following error:

Error: Customer <customer_id> does not have card with ID tok_visa
    at StripeError.generate (Error.js:10:20)
    at res.toJSON.then.Error_js_1.StripeAPIError.message (RequestSender.js:105:54)
valid martenBOT
bright pulsar
slender zodiac
#

I think the code of interest to this error should only mainly be the following two snippets:

  1. How I create a customer:
const customer = await stripe.customers.create({
          name: fullName,
          email: email,
          metadata:{
              credit_card_number: creditCardNumber,
              expiry_month: expiryMonth,
              expiry_year: expiryYear,
              cvv:cvv,
              address:address,
              city:city,
              state:state,
              zipCode:zipCode,
          }
        });

  1. How I am trying to charge that customer:
const charge = await stripe.charges.create({
            amount: amount,
            currency: 'usd',
            source: 'tok_visa',
            customer: customerId
        });

I will remove the metadata and switch to payment intents but I think the problem will still persist. How can I add a card for the customer in test mode or broadly speaking, how can I solve this?

bright pulsar
#

I recommend you to drop the code you currently have and explore the guides I shared with you, and then start over. This error message is only relevant to the code you shared, however it has nothing to do with what you're trying to achieve and uses outdated APIs.

slender zodiac
#

Hmm I see. Thanks for your help!

#

If there is no easier way to accomplish this, kindly tell me if I understand the whole thing correctly this time:

cyan fox
#

hi! I'm taking over this thread.

slender zodiac
#

Aoa Hi!

cyan fox
#

let me know if you have any other questions

slender zodiac
#

Should I give a small recap of what I am trying to do?

#

Very briefly, I am just trying to create a customer, store the id of the customer in my db and then every time a user wants to make a purchase, charge the associated customer_id.

cyan fox
#

got it

slender zodiac
#

I have been told that I should use setup intents for this. Is there a simpler way? One that would allow me to make minimal changes to what I already have?

cyan fox
slender zodiac
#

I see! Thanks!

If I go for Checkout Sessions, can I do this (all on client side):

Step 1: Creating a customer

const customer = await stripe.customers.create({
          name: fullName,
          email: email,
        });

Step 2: Attaching a payment method to the customer:

const checkoutSession = await stripe.checkout.sessions.create({
      payment_method_types: ["card"],
      mode: "setup",
      customer: customer.id,
      success_url: `<what-should-I-put-here-on-localhost>`,
      cancel_url: `<what-should-I-put-here-on-localhost>`
    });

Step 3: Charge a payment when they buy a product:

const paymentIntent = await stripe.paymentIntents.create({
  amount: 2000,
  currency: 'usd',
  automatic_payment_methods: {
    enabled: true,
  },
  customer: customerId,
});
cyan fox
#

If I go for Checkout Sessions, can I do this (all on client side):
everything has to be done on the backend side

#

and in step 3 you forgot to set the payment_method property

#

other that than, it looks correct

slender zodiac
cyan fox
slender zodiac
cyan fox
#

Checkout Session in setup mode would be the simplest option yes

slender zodiac
#

Oh so:

Step 1: Creating a customer

const customer = await stripe.customers.create({
          name: fullName,
          email: email,
        });

Step 2: Attaching a payment method to the customer:

const checkoutSession = await stripe.checkout.sessions.create({
      payment_method_types: ["card"],
      mode: "setup",
      customer: customer.id,
      success_url: `<what-should-I-put-here-on-localhost>`,
      cancel_url: `<what-should-I-put-here-on-localhost>`
    });

Step 3: Getting payment methods for customer when they buy a product:

const paymentMethods = await stripe.paymentMethods.list({
  customer: '{{CUSTOMER_ID}}',
  type: 'card',
});

Step 4: Charge a payment from one of their payment methods:

const paymentIntent = await stripe.paymentIntents.create({
  amount: 2000,
  currency: 'usd',
  automatic_payment_methods: {
    enabled: true,
  },
  customer: customerId,
  payment_method: paymentMethods[0].id
});
slender zodiac
cyan fox
#

you forgot step 2.5 : redirect the user to the Checkout Session URL so they can entier their payment details.

slender zodiac
#

I see!! Thanks!!

cyan fox
#

and step 4: you can remove automatic_payment_methods and you should add confirm:true and return_url, as mentionned in the link I shared

slender zodiac
#

got it! thank you so much!!

#

the urls can be localhost urls over http right?

#

cuz I am in test mode

#

also, if everything checks out, there was this last thing about client_secret that was confusing... what is it referring to and where/how do I get it?

cyan fox
#

yes you can test everything in localhost

#

also, if everything checks out, there was this last thing about client_secret that was confusing... what is it referring to and where/how do I get it?
if the PaymentIntent fails because the bank requires the user to go though 3DS, then you'll need to retrieve the client_secret of the PaymentIntent to try to re-confirm the PaymentIntent on the frontend with https://stripe.com/docs/js/payment_intents/confirm_card_payment#stripe_confirm_card_payment-attached
but don't worry about this for now. first, make sure that everything else works.

slender zodiac
#

Alrighty! I will get to it then. Thanks for all your help Soma and Vanya.