Selecting an existing payment method then go back and choose another existing payment method does not work.

Created on 18 January 2024, over 1 year ago
Updated 8 July 2024, about 1 year ago

Selecting an existing payment method then go back and choose another existing payment method does not work.

I think this is due to the fact that in StripeReview->buildPaneForm(), we only update the payment_method of the PaymentIntent if $intent->status === PaymentIntent::STATUS_REQUIRES_PAYMENT_METHOD

However, the first time StripeReview->buildPaneForm completes, the PaymentIntent now has a status of requires_confirmation. So if we go back and pick another existing payment method, the status of PaymentIntent still is requires_confirmation thus the code that updates the payment method of the PaymentIntent is not executed anymore.

For my client's website, I have commented out the
&& ($intent->status === PaymentIntent::STATUS_REQUIRES_PAYMENT_METHOD)
part and it solves the problem. We can now switch between existing payment methods.

What do you guys think?

πŸ› Bug report
Status

Closed: duplicate

Version

1.1

Component

Code

Created by

πŸ‡«πŸ‡·France nicolas bouteille

Live updates comments and jobs are added and updated live.
Sign in to follow issues

Comments & Activities

  • Issue created by @nicolas bouteille
  • πŸ‡«πŸ‡·France nicolas bouteille

    In this piece of code, we also retrieve the order's payment_method
    $payment_method = $this->order->get('payment_method')->entity;
    but we forget to check if the $payment_method is not null before using it
    $payment_method->getRemoteId();
    the only thing we check is if
    !$this->order->get('payment_method')->isEmpty()
    but the entity_reference field can have a target_id that references the id of a payment_method that has been deleted since. Leading to $payment_method object being null.
    if I'm not mistaken
    assert($payment_method instanceof PaymentMethodInterface);
    is only here to help for code autocomplete, but does not stop the code execution.
    So $payment_method->getRemoteId(); throws an Exception or a PHP error "trying to call ->getRemoteId() on null..."
    Here is what the if statement looks like on our website now to solve this :

    if (
      !$this->order->get('payment_method')->isEmpty() 
      && $payment_method = $this->order->get('payment_method')->entity
    ) {
  • πŸ‡ΊπŸ‡ΈUnited States TomTech

    Marking this as a duplicate of πŸ› Payment taken from the wrong card Fixed , as the root cause is the same...if a payment method is changed, we need to minimally update the paymentIntent, and possibly create a new one.

    This is performed at a lower level, (whenever the order is updated, if the payment method is changed), which should prevent it from cropping up in other scenarios.

    We could try and be more surgical in determining if we need to update the paymentIntent vs creating a new one, but since it is unlikely someone would continually swap between methods (more likely during development/qa), creating a new one when the method is changed is likely sufficient.

  • Assigned to TomTech
  • Status changed to Closed: duplicate about 1 year ago
  • πŸ‡ΊπŸ‡ΈUnited States TomTech
Production build 0.71.5 2024