Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Restore magento quote after payment was refused

Tags:

php

magento

I'm creating a magento payment extension which does the following:

When the user clicks on checkout in the merchant site, he gets redirected to a web site (like paypal) where he inputs his payment data. If the payment method fails, the user gets redirected to the merchant site.

However, it appears that the quote is no more active.

What are the possibilities that make it possible to the end user to reuse his quote ?

A few possibilities would be :

  • Duplicating the quote if the user gets back
  • Retrieve the quote and set it to active so that it shows again

Here is some of the code I use in my payment model:

To initialize the payment method to pending_payment

/**
 * Instantiate state to pending_payment
 * @param
 * @param
 */
public function initialize($paymentAction, $stateObject)
{
    $state = Mage_Sales_Model_Order::STATE_PENDING_PAYMENT;
    $stateObject->setState($state);
    $stateObject->setStatus(Mage_Sales_Model_Order::STATE_PENDING_PAYMENT);
    $stateObject->setIsNotified(false);
}

To redirect to the payment method (the url will then redirect to the remote host)

/**
 * Checkout redirect URL getter for onepage checkout
 *
 * @see Mage_Checkout_OnepageController::savePaymentAction()
 * @see Mage_Sales_Model_Quote_Payment::getOrderPlaceRedirectUrl()
 * @return string
 */

public function getOrderPlaceRedirectUrl()
{
    return Mage::getUrl('pay/payment/redirect');
}

In case that the payment fails, the user will come back at the url /pay/payment/fail (I already know how to create a controller for this, my only problem is to reactivate the quote).

like image 638
edi9999 Avatar asked Mar 17 '23 01:03

edi9999


1 Answers

I found out how to do this (many modules do it too : Paypal, Authorizenet, Stripe)

You just have to first cancel that order (using the registerCancellation method), then you load the quote, setIsActive to 1 and remove the ReservedOrderId field.

public function cancelAction()
{
    $session = Mage::getSingleton('checkout/session');
    if ($session->getLastRealOrderId())
    {
        $order = Mage::getModel('sales/order')->loadByIncrementId($session->getLastRealOrderId());
        if ($order->getId())
        {
            //Cancel order
            if ($order->getState() != Mage_Sales_Model_Order::STATE_CANCELED)
            {
                $order->registerCancellation("Canceled by Payment Provider")->save();
            }
            $quote = Mage::getModel('sales/quote')
                ->load($order->getQuoteId());
            //Return quote
            if ($quote->getId())
            {
                $quote->setIsActive(1)
                    ->setReservedOrderId(NULL)
                    ->save();
                $session->replaceQuote($quote);
            }

            //Unset data
            $session->unsLastRealOrderId();
        }
    }

    return $this->getResponse()->setRedirect( Mage::getUrl('checkout/onepage'));
}
like image 50
edi9999 Avatar answered Apr 02 '23 19:04

edi9999