Question

I just upgrade from 1.8, where this used to work. Now when a cart discount is applied to an order, Magento 1.9.2.1 shows the right prices, taxes and discount in the order, but it passes different values to Paypal which results in a different payment and an IPN of suspected fraud.

This is a shop with VAT=22%.

The tax configuration:

Tax configuration

Order with right amounts but Paypal charges a different amount 76.32€ vs 79.92€ and Magento reports a suspected fraud

enter image description here

and this are the values that were passed by Magento (omitting the non relevant ones):

[url] => https://api-3t.paypal.com/nvp
[BMCreateButton] => Array
    (
        [METHOD] => BMCreateButton
        [BUTTONCODE] => TOKEN
        [BUTTONTYPE] => PAYMENT
        [L_BUTTONVAR0] => subtotal=81.89
        [L_BUTTONVAR1] => tax=14.41
        [L_BUTTONVAR2] => shipping=0.00

        [L_BUTTONVAR7] => discount=19.98

        [VERSION] => 72.0

        [BUTTONSOURCE] => Magento_Cart_Community
    )

Can you please help to fix this?

Was it helpful?

Solution

PayPal doing the following math: Subtotal + Tax - Discount and receive a Total based on this calculation. While all the figures in Magento sales order are correct there is no way to properly send this amount combinations since PayPal expect calculations made based on prices excluding tax, not including (in your example discount is applied on amount including tax, this is where the difference goes from!). The only way to receive a proper amounts in this case is to pass only subtotal field with Grand Total value, otherwise we will need to change discount to excluding tax which will confuse the customer.

So, to summarize this part:

   protected function _getOrderData(Mage_Sales_Model_Order $order)
        {
            $request = array(
                'subtotal'      => $this->_formatPrice($order->getBaseSubtotal()),
                'tax'           => $this->_formatPrice($order->getBaseTaxAmount()),
                'shipping'      => $this->_formatPrice($order->getBaseShippingAmount()),
                'invoice'       => $order->getIncrementId(),
                'address_override' => 'true',
                'currency_code'    => $order->getBaseCurrencyCode(),
                'buyer_email'      => $order->getCustomerEmail(),
                'discount'         => $this->_formatPrice(
                    $order->getBaseGiftCardsAmount()
                    + abs($order->getBaseDiscountAmount())
                    + $order->getBaseCustomerBalanceAmount()
                ),
            );

Needs to be replaced with (Haven't tested it):

protected function _getOrderData(Mage_Sales_Model_Order $order)
    {
        $request = array(
            'subtotal'      => $this->_formatPrice($order->getBaseGrandTotal()),
            'invoice'       => $order->getIncrementId(),
            'address_override' => 'true',
            'currency_code'    => $order->getBaseCurrencyCode(),
            'buyer_email'      => $order->getCustomerEmail(),
            ),
        );

OTHER TIPS

Just a little comment, there's a typo on the solution. There's an unwanted closing parenthesis

protected function _getOrderData(Mage_Sales_Model_Order $order)
{
    $request = array(
        'subtotal'      => $this->_formatPrice($order->getBaseGrandTotal()),
        'invoice'       => $order->getIncrementId(),
        'address_override' => 'true',
        'currency_code'    => $order->getBaseCurrencyCode(),
        'buyer_email'      => $order->getCustomerEmail(),
    );
Licensed under: CC-BY-SA with attribution
Not affiliated with magento.stackexchange
scroll top