#MidnighttFoxx
1 messages · Page 1 of 1 (latest)
Hi there
hello. how are you?
Good thanks. Hope you are doing well, too. Which Mobile SDK are you using?
react native
Gotcha. And you are looking to pre-fill certain parts of Card Form? Or what are you trying to accomplish exactly?
essentially i have the users store their credit card information elsewhere and then can pick from a dropdown the card they want to fill to cardField with to actually make the payment
Hmmm that doesn't really make sense. Why use the CardForm at all here then?
The CardForm is for collecting a new payment method.
If you already have the PaymentMethod stored then there is really no reason to use CardForm
Also I assume you are aware of the PCI implications of handling these raw PANs, yes?
i am giving the users an option to either enter an unstored card or to pick from one they alreadt have stored, i also havent been able to find a way to use the stored cards to have the payments actually go through
Lets back up one sec.
also yes i am aware. the app is not launched yet so there is no fear there right now
Are you handling card details yourself or are you always collecting them through Stripe?
i wanted to do it all through stripe but i could not get that working
Okay gotcha, that is definitely the recommended way and I'm happy to help you get that working.
perfect thank you
So what part are you blocked at? It sounds like you are able to successfully collect card details the first time and create a payment?
i tested the card input i created with the 4242 test card and the payment succesfully went through
Great
i am not sure how to actually store the credit card after that
Gotcha
So https://stripe.com/docs/payments/save-during-payment-cards-only is the guide you want to follow
Are you currently creating a Customer object server-side?
yes
Nah not yet
So when you create your PaymentIntent go ahead and also pass setup_future_usage: 'off_session': https://stripe.com/docs/api/payment_intents/create#create_payment_intent-setup_future_usage
That way, when you confirm the PaymentIntent client-side, the new PaymentMethod will be automatically attached to the Customer
And you can then charge it again in the future without needing to collect details again
Give that a try and let me know if you see the PaymentMethod attached to the Customer successfully.
sure thing thank you
Then we can talk about how to charge that PaymentMethod later on
i do see the card added to the user
Okay perfect. So when a Customer returns to your App you are going to use https://stripe.com/docs/api/payment_methods/customer_list to list out any attached PaymentMethods
And you will build out a UI to allow them to select one of these PaymentMethods if they want to charge a saved PaymentMethod
If they choose a saved PaymentMethod, then you create and confirm a PaymentIntent server-side to charge it again as we show here: https://stripe.com/docs/payments/save-during-payment-cards-only?platform=react-native#react-native-create-payment-intent-off-session
is this all in the frontend?
also i am not sure if the way i am creating a customer is correct
The above is all on the server
gotcha
How are you creating the Customer?
i call const customer = await stripe.customers.create({
name,
email,
phone<
didnt mean to send that in three messages
Yeah that is fine
ok, but i am always passing in the same name email and phone for the time being
is that going to cause problems
it seems like a new customer is created each time i create a payment intent
We don't de-duplicate for you
You can create multiple Customers with same info if you want.
But really you will need to add an authentication system to your App
So that you pair a Customer ID to a user
Gotcha. Well you can test using the same info, that's fine.
am i pulling the customer id from the customer i created with the above line
What do you mean by that?
Yes you should pass customer.id to your PaymentIntent
If that's what you are asking
in the link you provided it does listPaymentMethods(
'cus_MbuuJzuEguLdkH',
{type: 'card'}
)
where is the first parameter coming from
gotcha
so once ive created that method in the backend how do i actually get the saved cards
In what sense? That list method returns you the saved cards
Specifically the PaymentMethod object represents a card
And you want to pass the PaymentMethod ID to a PaymentIntent to charge a saved card
so i should have two payment intents: 1. if the user inputs a new card and 2. if the user selects a pre-existing card from a list i created in the UI
Two different flows, but they both use a PaymentIntent.
You don't need to create two PaymentIntents every time the user visits your page
When they click "pay" you execute the "new card flow" or the "saved card flow"
ah
Basically you fetch your backend when they hit your "pay" button
So on page load you fetch backend to display any saved PaymentMethods, then you fetch again on "pay" to execute the payment flow
so do i call in the backend both stripe.customers.listPaymentMethods and stripe.paymentMethods.list
Just use stripe.customers.listPaymentMethods
It is confusing that both exist but basically just ignore stripe.paymentMethods.list
im sorry, im a little lost on how to display the cards or do the separate flows
No problem
What is confusing you specifically?
What steps have you done so far?
when i tried to fetch on initial page load i got a bunch of errors like maximum call stack size exceeded and exception in host function <unknown>
Are you using useEffect?
yea
Can you share your code?
👋 stepping in on behalf of bismarck since he has to step away.
hello
what's the full stack trace for the error(s) that you get? And i see that the constants declared seem to have an issue too?
those consts are just unused right now
[Unhandled promise rejection: RangeError: Maximum call stack size exceeded.]
at node_modules@babel\runtime\helpers\regeneratorRuntime.js:86:13 in tryCatch
at node_modules@babel\runtime\helpers\regeneratorRuntime.js:66:31 in <anonymous>
- ... 89 more stack frames from framework internals
[Unhandled promise rejection: Error: Exception in HostFunction: <unknown>]
at node_modules\react-native\Libraries\BatchedBridge\MessageQueue.js:321:6 in enqueueNativeCall
at node_modules\react-native\Libraries\BatchedBridge\NativeModules.js:149:8 in nonPromiseMethodWrapper
at node_modules\react-native\Libraries\Core\Timers\JSTimers.js:440:2 in createTimer
at node_modules\react-native\Libraries\Core\Timers\JSTimers.js:217:15 in setTimeout
at node_modules@firebase\firestore\dist\rn\prebuilt.rn-3ca9030c.js:11762:37 in <anonymous>
at node_modules@firebase\firestore\dist\rn\prebuilt.rn-3ca9030c.js:11756:15 in n.targetChanges.forEach$argument_0
etc. etc.
okay, that's interesting, does the fetch successfully hit your server?
i believe so
my goal with this fetch was to get the stored credit cards to display them
its the same fetch im making when doing the actual payment
i cant even load the screen, so my guess is it doesnt hit the server
when you say you can't even load the screen, do you mean the application's screen/page isn't loading for you?
when i navigate to the screen with this fetch call it immediately gives me an error
You implemented the server right? Can you check the logs of the server to be sure?
the last log on the server was like 20 minutes ago when i last sent in a payment
so it looks like your fetch did hit the server am i right?
since you're able to view the log on the server where you sent in a payment?
yea but that was for when i pressed the pay button after inputting card details
the problem im having is getting the stored cards for the user and displaying them
to confirm - is that screenshot of the fetch code you shared going to retrieve the stored cards for the user as well?
that was the intention, but it doesnt seem like it will
i make that call in the frontend
in the backend i call stripe.customers.listPaymentMethods
however i dont do anything with that call
can you comment out the entire fetch and the corresponding useEffect? what happens then?
i am able to type into the cardField and successfully complete the payment
i need to get the stored cards, and display them for the user to then pick and if they pick one use that in the paymentIntent
Can you add more log lines to the inside of your fetch function, namely :
- just before
const response... - just before
const data... - after the
ifcondition
then let me know what's the output when you try to run
i get output right before response but thats it
is this error from your server? Unhandled promise rejection: Error: Exception in HostFunction: <unknown>
you mentioned that you're able to complete payment after pressing the pay button - are you doing another fetch call elsewhere to get the PaymentIntent?
bismarck told me that i should be doing one fetch on page load to grab the stored cards and display them to the user to pick from and then a second fetch when the user actually completes the payment when clicking the pay button
i think you should try simplifying your code first, and start from there i.e. remove all other functions and methods, and just try to fetch on page load, and display what you've fetched
honestly, it's a bit difficult to try and troubleshoot without looking your entire application code
could you explain to me how i am supposed to get the values from my call to stripe.customers.listPaymentMethods
i'm a bit confused, where are you calling stripe.customers.listPaymentMethods?
in my index.js file in my backend
alright, what do you mean by how are you supposed to get the values? When you call this method, you will get the corresponding response / values
right so i have a function const paymentMethods = await stripe.customers.listPaymentMethods(
customer.id
{type: 'card'})
but what do i do with that paymentMethods const
then i assume you would return it to your frontend and display it
for example, if you're using Express in your backend, you can return values using https://expressjs.com/en/4x/api.html#res
even if i do that it doesnt resolve the issue that i can't fetch on initial page load
yep i get that. Unfortunately i don't know why you can't fetch on initial page load too and my suggestion for you is to simplify your application to the bare minimum to try and figure out what's the issue
ok thank you
i havent resolved that error yet, but i am having the problem where every time i create a paymentIntent it creates a new customer which in turn means there is never going to be a card to display
like what bismarck mentioned before, you would want to add an authentication system to your App so that you pair a Customer ID to a user. When a user logs in, you will always retrieve / use that specific Customer paired to them.
for now, if you're just testing, you can choose to always retrieve the same Customer (instead of always creating a new one)