Search code examples
phplaravelstripe-payments

Handling invoice.payment_succeeded event with Stripe checkout Laravel Cashier


I'm migrating my Laravel Cashier setup over to utilise the Stripe checkout feature. My platform offers both: subscriptions and one-off charges. One of these one-off charges is the ability to replenish SMS credits in the user's account, originally, I was using the invoicePrice method and pass through some metadata:

$addonItemPrice = Cashier::stripe()->prices->retrieve($addonItem->stripe_id);
Auth::user()->invoicePrice(
    $addonItem->stripe_id, 1, [
        'metadata' => [
            'is_addon' => true,
            'is_sms_addon' => true,
            'created_at' => Carbon::now(),
            'user_id' => Auth::id(),
            'addon_id' => $addonItem->id,
            'addon_quantity' => $addonItem->quantity,
            'apply_credit_balance' => true,
        ],
    ]
);

I'm then listening for a webhook event for invoice.payment_succeeded to know for sure to add SMS credits to their account:

/**
 * Handle received Stripe webhooks.
 */
public function handle(WebhookReceived $event)
{
    match ($event->payload['type']) {
        'customer.subscription.created' => $this->handleSubscriptionCreated($event->payload),
        'invoice.payment_succeeded' => $this->handleInvoicePaymentSucceeded($event->payload),
        default => null
    };
}

However, I'm now migrating to using Stripe's checkout, so it now looks like:

$charge = $user->checkout([$addonItemPrice->id => 1], [
    'success_url' => "$frontendURL"."account/billing/checkout/success/",
    'cancel_url' => "$frontendURL"."account/billing/add-ons/",
    'metadata' => [
        'is_addon' => true,
        'is_sms_addon' => true,
        'created_at' => Carbon::now(),
        'user_id' => Auth::id(),
        'addon_id' => $addonItem->id,
        'addon_quantity' => $addonItem->quantity,
        'apply_credit_balance' => true,
    ],
]);

But I'm not getting an invoice.payment_succeeded event at all now. It seems that my metadata is now associated with the checkout.session.completed event.

Should I migrate to this new event, or is this going to be unreliable? I only want such event to trigger when the invoice payment has succeeded


Solution

  • From your post, I don't have a lot of context but am assuming that the price is one-time and not recurring (else you'd still expect an invoice.payment_succeeded to fire, even with checkout).

    I'm not familiar with what the laravel library supports, but looking at the params of this checkout function it might be a 1-to-1 with the Stripe checkout.sessions.create function.

    In which case, you might get what you want with the following params:

    'invoice_creation' => [
       'enabled' => true,
       'invoice_data' => [
          'metadata' => [
             // your metadata
          ]
       ]
    ]
    

    https://docs.stripe.com/api/checkout/sessions/create?lang=php#create_checkout_session-invoice_creation-invoice_data-metadata