Stripe removed invoice.payment_intent in the basil API and it quietly broke my failed-payment workflow
Description and use
Stripe removed invoice.payment_intent in API version 2025-03-31.basil, breaking failed-payment workflows. The fix is to query invoice_payments with expand[]=data.payment.payment_intent and use last_payment_error.decline_code.
Problem
Stripe’s API version 2025-03-31.basil removed the invoice.payment_intent field, causing a failed-payment workflow to stop silently when the code attempted to access an undefined payment intent.
Outcome
The updated approach restores failed-payment handling for hard declines, soft declines, and 3DS cards in the new API version.
Workflow
- 1. Send GET /v1/invoice_payments?invoice={invoice_id}&limit=1&expand[]=data.payment.payment_intent
- 2. Retrieve data[0].payment.payment_intent
- 3. Access last_payment_error.decline_code from the payment intent
- 4. Proceed with retry or notification logic
Evidence
From that version the invoice doesn't have payment_intent, charge or paid anymore.
Ask for the invoice's payments and expand the payment intent in the same call: GET /v1/invoice_payments?invoice=in_123&limit=1&expand[]=data.payment.payment_intent
- Record date: 2026-10-06T07:55:46.487Z