I am successfully able to process Stripe payments in react using the following:
const processPayment = async () => {
const url = '/.netlify/functions/charge-card';
const newItems = items.map(({ id, quantity }) => ({
id,
quantity,
}));
const stripe = await loadStripe(publishableKey);
const { data } = await axios.post(url, { items: newItems });
await stripe.redirectToCheckout({ sessionId: data.id });
};
This is the only method that will work for me
exports.handler = async (event, context) => {
const { items } = JSON.parse(event.body);
const allItems = await getProducts();
const cartWithProducts = items.map(({ id, quantity }) => {
const item = allItems.find(p => p.id === id);
return {
...item,
quantity,
};
});
const lineItems = cartWithProducts.map(product => ({
price_data: {
currency: 'usd',
product_data: {
name: product.name,
},
unit_amount: product.price,
},
quantity: product.quantity,
}));
const session = await stripe.checkout.sessions.create({
payment_method_types: ['card'],
line_items: lineItems,
mode: 'payment',
success_url: `${process.env.URL}/success`,
cancel_url: `${process.env.URL}/cancelled`,
});
console.log(lineItems);
return {
statusCode: 200,
body: JSON.stringify({
id: session.id,
}),
};
However, I don't want to use await stripe.redirectToCheckout({ sessionId: data.id });
because I don't want to be redirected to Stripe's site. I want to do something like this:
return (
<StripeCheckout
label={'Pay Now'}
name={'CRWN Clothing Ltd.'}
billingAddress
shippingAddress
image={'https://svgshare.com/i/CUz.svg'}
description={`Your total is $${price}`}
amount={priceForStripe}
panelLabel={'Pay Now'}
token={processPayment}
stripeKey={publishableKey}
/>
This shows the popup and allows me to enter all the info and submit the payment however nothing actually happens. I don't know if it has something to do with the sessionId and data.id. Is there another function I can use instead of stripe.redirectToCheckout that would process the info?
OK I got it to work. Here is my processPayment:
const processPayment = token => {
const url = '/.netlify/functions/charge-card';
const options = {
method: 'POST',
headers: {
'Accept': 'application/json',
'Content-Type': 'application/json;charset=UTF-8',
},
body: JSON.stringify({
amount: priceForStripe,
token,
}),
};
fetch(url, options)
.then(response => {
alert('Payment Successful');
}).catch(error => {
console.log('Payment error:', error);
alert('There was in issue with your payment. Please make sure you use the provided credit card.');
});
};
My StripeCheckoutButton:
<StripeCheckout
label={'Pay Now'}
name={'CRWN Clothing Ltd.'}
billingAddress
shippingAddress
image={'https://svgshare.com/i/CUz.svg'}
description={`Your total is $${price}`}
amount={priceForStripe}
panelLabel={'Pay Now'}
token={processPayment}
stripeKey={publishableKey}
/>
I really didn't need access to the items just the total price so I changed my exports.handler to:
exports.handler = async (event, context) => {
const data = JSON.parse(event.body);
const body = {
source: data.token.id,
amount: data.amount,
currency: 'usd',
};
await stripe.charges.create(body, (stripeErr, stripeRes) => {
if (stripeErr) {
return {
statusCode: 500,
body: stripeErr,
};
} else {
return {
statusCode: 200,
body: stripeRes,
};
}
});
};
Now everything works. I can use the popup from stripe and not be redirected and the payments process completely on stripes end.