Reputation: 466
I just finished setting up payments through stripe on PHP using their payment intents API and forgot about having to add the products/items the user has just purchased.
Looking through the API Reference I didn't see anything where I could add items to the payment intent so I could retreive what was purchased later on in the webhook.
Do I need to do my own magic and somehow add the items to the metadata array or is there something that i'm missing here?
Upvotes: 15
Views: 11074
Reputation: 3430
The previous answer is not entirely correct. Perhaps the Stripe API documentation has changed. So what needs to be done:
// Step 1: Create an invoice by passing the customer_id.
const stripe = require('stripe')('YOUR_STRIPE_SECRET_KEY');
async function createInvoice(customer_id) {
try {
const invoice = await stripe.invoices.create({
customer: customer_id,
});
return invoice;
} catch (error) {
console.error('Error creating invoice:', error);
throw error;
}
}
// Step 2: Create an invoice item for the invoice obtained from the previous step, by passing the customer_id, invoice_id, and either price_id or amount and currency.
async function createInvoiceItem(customer_id, invoice_id, price_id, amount, currency) {
try {
const invoiceItem = await stripe.invoiceItems.create({
customer: customer_id,
invoice: invoice_id,
price: price_id, // or amount and currency, depending on your choice
});
return invoiceItem;
} catch (error) {
console.error('Error creating invoice item:', error);
throw error;
}
}
// Step 3: Finalize the invoice to set its status to "open" and automatically receive the payment intent.
async function finalizeInvoice(invoice_id) {
try {
const finalizedInvoice = await stripe.invoices.finalizeInvoice(invoice_id);
return finalizedInvoice;
} catch (error) {
console.error('Error finalizing invoice:', error);
throw error;
}
}
// Step 4: Request the payment intent for the invoice.
async function getPaymentIntent(invoice_id) {
try {
const paymentIntent = await stripe.paymentIntents.create({
invoice: invoice_id,
});
return paymentIntent;
} catch (error) {
console.error('Error getting payment intent:', error);
throw error;
}
}
// Usage of all steps:
async function main() {
try {
const customer_id = 'YOUR_CUSTOMER_ID';
// Step 1: Create an invoice
const invoice = await createInvoice(customer_id);
console.log('Created invoice:', invoice);
// Step 2: Create an invoice item
const price_id = 'YOUR_PRICE_ID'; // or use amount and currency if not using Price API
const invoiceItem = await createInvoiceItem(customer_id, invoice.id, price_id, 1000, 'usd');
console.log('Created invoice item:', invoiceItem);
// Step 3: Finalize the invoice and get the payment intent
const finalizedInvoice = await finalizeInvoice(invoice.id);
console.log('Finalized invoice:', finalizedInvoice);
// Step 4: Request the payment intent
const paymentIntent = await getPaymentIntent(invoice.id);
console.log('Payment intent:', paymentIntent);
} catch (error) {
console.error('Error:', error);
}
}
main();
Upvotes: 4
Reputation: 8162
I'm using node.js. Here's what worked for me:
Step #5 response will contain the client_secret
value that can be sent to the client for payment capture.
const customer = ...
const invoiceItem = await stripe.invoiceItems.create({
customer: ...
price_data: { ... }
})
const invoice = await stripe.invoices.create({
customer: ...
})
const finalInvoice = await stripe.invoices.finalizeInvoice(
invoice.id
)
const paymentIntent = await stripe.paymentIntents.retrieve(
finalInvoice.payment_intent
)
res.send({ secret: paymentIntent.client_secret })
Upvotes: 14
Reputation: 2906
PaymentIntents do not track any sort of product that's connected to the purchase (just an amount). In order to link Products to a payment, you'd want to use Invoices which will generate a PaymentIntent as part of the process.
Upvotes: 21