PayPal IPN Error: Order Currency Check failed. Modified PayPal VM code settings

Started by entalzar, October 29, 2012, 11:00:00 AM

Previous topic - Next topic

entalzar

My customer had another vendor setup his VirtueMart store and he modified a lot of code. In this case my customer has receive two separate errors when a person completes their orders which are over 25,000 JPY. Below is one example:

During a paypal transaction on your site the received amount didn't match the order total.
                        Order ID: 159_b1bf5beea774983c4d5ebfeb1ac2.
                        Order Number: 159_b1bf5beea774983c4d5ebfeb1ac2.
                        The amount received was: 27090 JPY.
                        It should be: 0 .


I checked the PayPal configuration in VM and noticed a lot of extra code. Please see the below code:

<?php

/** Read current Configuration ***/
include_once(CLASSPATH ."payment/ps_paypal_conf.cfg.php");
include_once(CLASSPATH ."payment/ps_paypal_conf.php");

$db_conf = new ps_DB;
$ps_paypal_conf = new ps_paypal_conf();
$NOTIFY_DEBUG = false;

if ($my->id == null){
    $id_user = $_SESSION['auth']["user_id"];
}else {
    $id_user = $my->id;
}

$url = "https://www.paypal.com/cgi-bin/webscr";
$return_url = SECUREURL ."index.php?option=com_virtuemart&page=checkout.result_confirmation&order_number=";
$notify_url = SECUREURL ."administrator/components/com_virtuemart/notify_gen_transaction.php";
$cancel_return = SECUREURL ."index.php?option=com_virtuemart&page=checkout.result_confirmation&cancel=1";
$errorurl = $return_url;

//$_SESSION["payement_transid"] ="";
isset($_SESSION["payement_transid"])? $transid = $_SESSION["payement_transid"]: $transid = 0;
isset($_SESSION["payement_order_number"])? $order_number = $_SESSION["payement_order_number"]: $order_number=0;

//Calc total for paypal

if (!isset ($discount_total)) $discount_total = 0;
if (!isset ($total)) $total = 0;
if (!isset ($shipping_total)) $shipping_total = 0;

$paypal_total = $total-$discount_total;
if ($auth["show_price_including_tax"] == 0) $paypal_total += $tax_total;

$_SESSION['total_amount'] = round( $paypal_total, 2);
$_SESSION['shipping_amount'] = sprintf("%.2f", $shipping_total);


//Create URL string to save all Request parameters
$requests = JRequest::get();
$confirmurl="";
foreach( $requests as $name => $value ) {
    $confirmurl .= $name . "=" . $value . "&";
}
if(!empty($zone_qty)) $confirmurl .= "&zone_qty=$zone_qty";


//If transaction has already been confirm then User payed and hit back button => Clean up session and redirect to thankyou
if($ps_paypal_conf->payement_is_confirmed($transid, $db_conf)){
         if ($NOTIFY_DEBUG) echo "payement is confirmed";
        //Order has been confirmed so clean up and reload modified SESSION from database
        $order_number = $ps_paypal_conf->cleanup_session($transid, $db_conf);
        // Redirect to thankyou page
        if ($NOTIFY_DEBUG) echo "should redirect to $return_url . $order_number";
        vmRedirect( $return_url . $order_number);

}elseif (!(empty($transid))){
        //User Came back to checkout without having payed, simply update session data in DB
        $sql = "SELECT * from #__vm_orders_temp WHERE id='".$transid."'";
        $db_conf->query($sql);
        if(!$db_conf->next_record()){
            //Transaction is not in DB at all, something is wrnog clean up ...
            $ps_paypal_conf->cleanup_session_vars();
            $transid = "";
            $_SESSION['total_amount'] = round( $paypal_total, 2);
            $_SESSION['shipping_amount'] = sprintf("%.2f", $shipping_total);
        }else{
            if ($NOTIFY_DEBUG) echo "TransID not empty updating DB transid = $transid";
            $sessioncontent=base64_encode(serialize($_SESSION));
            $sql = "UPDATE #__vm_orders_temp SET urlpost='".addslashes($confirmurl)."', urlerror='".addslashes($errorurl)."', sessioncontent='".addslashes($sessioncontent)."' , modifiedtime=NOW() WHERE id='".$transid."'";
            $db_conf->query($sql);
        }

}

if (empty($transid)){
    //First time on Checkout page save temporary transaction information

    //Get Order Number using default checkout function
    include_once(CLASSPATH ."ps_checkout.php");
    $ps_checkout = new ps_checkout();
    $order_number = $ps_checkout->get_order_number();
    if ($NOTIFY_DEBUG) echo "New ORDER NUMBER  = $order_number";

    // Add order Number to session value before saving to db
    $_SESSION["payement_order_number"]=$order_number ;
    $sessioncontent=base64_encode(serialize($_SESSION));

    //Save temporary transaction data to DB
    $sql = "INSERT INTO #__vm_orders_temp (`status`,`urlpost`,`urlerror`,`createdtime`,`modifiedtime`, `sessioncontent`, `order_number` , `user_id`) VALUES
   ('0','".addslashes($confirmurl)."','".addslashes($errorurl)."',NOW(),NOW(),'".addslashes($sessioncontent)."','".$order_number."','".$id_user. "')";
    $db_conf->query($sql);

    $_SESSION["payement_transid"] = $transid = $db_conf->last_insert_id();
}

if ($NOTIFY_DEBUG) print $_SESSION["payement_order_number"];



//Get user infos
$dbbt = new ps_DB;
$q = "SELECT * FROM jos_vm_user_info ";
$q .= "WHERE user_id ='".$id_user."' ";
$dbbt->query($q);


//Get coutry code
$db1 = new ps_DB();
$q = "SELECT country_2_code FROM #__vm_country WHERE country_3_code='".$dbbt->f('country'). "' ORDER BY country_2_code ASC";
$db1->query($q);


//**** START FORM CREATION *****//


if (GENERATE_TRANSACTION_ON_CONFIRMATION == 1) {
    //Form for including directly into checkout.index form
    //Defines all input variables off form
    $post_variables = Array(
        "cmd" => "_ext-enter",
        "charset" => "utf-8",
        "redirect_cmd" => "_xclick",
        "upload" => "1",
        "business" => PAYPAL_EMAIL,
        "receiver_email" => PAYPAL_EMAIL,
        "item_name" => $VM_LANG->_('PHPSHOP_ORDER_PRINT_PO_LBL').": ". $vendor_name,
        "order_id" => $transid,
        "invoice" => $order_number,
        "amount" => round( $paypal_total, 2),
        "shipping" => sprintf("%.2f", $shipping_total),
        "currency_code" => (!empty($_SESSION['product_currency']))? $_SESSION['product_currency'] : $_SESSION['vendor_currency'],

        "address_override" => "1",
        "first_name" => $dbbt->f('first_name'),
        "last_name" => $dbbt->f('last_name'),
        "address1" => $dbbt->f('address_1'),
        "address2" => $dbbt->f('address_2'),
        "zip" => $dbbt->f('zip'),
        "city" => $dbbt->f('city'),
        "state" => $dbbt->f('state'),
        "country" => $db1->f('country_2_code'),
        "email" => $dbbt->f('user_email'),
        "night_phone_b" => $dbbt->f('phone_1'),
        "cpp_header_image" => $vendor_image_url,

        "return" => $return_url . $order_number,
        "notify_url" => $notify_url,
        "cancel_return" => $cancel_return,
        "undefined_quantity" => "0",

        "test_ipn" => PAYPAL_DEBUG,
        "pal" => "NRUBJXESJTY24",
        "no_shipping" => "1",
        "no_note" => "1",
        "rm" => "2"
    );
}else{
//Form for using when Transaction already saved
    $tax_total = $db->f("order_tax") + $db->f("order_shipping_tax");
    $discount_total = $db->f("coupon_discount") + $db->f("order_discount");
    //Defines all input variables off form
    $post_variables = Array(
        "cmd" => "_xclick",
        "charset" => "utf-8",
        "business" => PAYPAL_EMAIL,
        "receiver_email" => PAYPAL_EMAIL,
        "item_name" => $VM_LANG->_PHPSHOP_ORDER_PRINT_PO_NUMBER.": ". $db->f("order_id"),
        "order_id" => $db->f("order_id"),
        "invoice" => $db->f("order_number"),
        "amount" => round( $db->f("order_subtotal")+$tax_total-$discount_total, 2),
        "shipping" => sprintf("%.2f", $db->f("order_shipping")),
        "currency_code" => $_SESSION['vendor_currency'],
        "first_name" => $dbbt->f('first_name'),
        "last_name" => $dbbt->f('last_name'),
        "address_street" => $dbbt->f('address_1'),
        "address_zip" => $dbbt->f('zip'),
        "address_city" => $dbbt->f('city'),
        "address_state" => $dbbt->f('state'),
        "address_country" => $dbbt->f('country'),
        "image_url" => $vendor_image_url,
        "return" => SECUREURL ."index.php?option=com_virtuemart&page=checkout.result&order_id=".$db->f("order_id"),
        "notify_url" => SECUREURL ."administrator/components/com_virtuemart/notify.php",
        "cancel_return" => SECUREURL ."index.php",
        "undefined_quantity" => "0",
        "test_ipn" => PAYPAL_DEBUG,
        "pal" => "NRUBJXESJTY24",
        "no_shipping" => "1",
        "no_note" => "1",
        "rm" => "2"
    );
}

//OLD WAY OF DOING chekout..... If in thankyou page then Transaction was already confirmed and we redirect to PAYPAL
if( $page == "checkout.thankyou" ) {
    $query_string = "?";
    foreach( $post_variables as $name => $value ) {
        $query_string .= $name. "=" . urlencode($value) ."&";
    }
    vmRedirect( $url . $query_string );
} elseif ($page=="checkout.index" )  {
    // Generate The form for the checkout button
    ?>
    <script type="text/javascript">
        var VIRTUEMART_URL="administrator/components/com_virtuemart/notify_gen_transaction.php";
        var VIRTUEMART_REQ_VAL ="save_transaction=1&transid=<?php echo $transid?>";
        var immoxmlhttp;
        var nb_tries=0;
        var max_tries=3;

        <?php if (GENERATE_TRANSACTION_ON_CONFIRMATION == 1) echo 'remove_original_submit_button();'; ?>

        function remove_original_submit_button(){
            document.adminForm.formSubmit.style.display="none";
            //document.getElementsByName("formSubmit")[1].style.display = "none";
        }

        function myXmlHttpReq(){
            if (window.XMLHttpRequest){
                var req = new XMLHttpRequest();
            }else if (window.ActiveXObject){
                var req = new ActiveXObject("Microsoft.XMLHTTP");
            }
            return req;
        }

        function sendReq(){
            immoxmlhttp = new myXmlHttpReq();
            immoxmlhttp.onreadystatechange = processCommentReqChange;
            immoxmlhttp.open("POST", VIRTUEMART_URL, true);
            immoxmlhttp.setRequestHeader("Content-Type","application/x-www-form-urlencoded");
            immoxmlhttp.send(VIRTUEMART_REQ_VAL);
            setLoadingImg();
        }

        function setLoadingImg(){
            img_req='<img src="images/stories/spin.gif">';
            ldimgdiv=document.getElementById("loadimgdivid");
            ldimgdiv.innerHTML=img_req;
        }

        function validateAndSentForm(){
            if(submit_order( document.adminForm )){
               VIRTUEMART_REQ_VAL += "&customernote=" + document.adminForm.customer_note.value;
               sendReq();
               return true;
            }
            else
                return false;
        }

        function processCommentReqChange(){
            if (immoxmlhttp.readyState == 4){
                 try{
                    // only if "OK"
                    if (immoxmlhttp.status == 200){
                       //alert(immoxmlhttp.responseText);
                        var r=immoxmlhttp.responseText;
                       var haserror=r.substring(r.indexOf("<error>"),r.indexOf("</error>")).replace("<error>","");
                        if(haserror==1){
                            errmsg= r.substring(r.indexOf("<errormsg>"),r.indexOf("</errormsg>")).replace("<errormsg>","");
                            alert(errmsg);
                        }
                        else{
                            //we submit the form
                            //document.forms[2].submit();
                            //postform=document.getElementById("postfinanceformid");

                          /*$transid = r.substring(r.indexOf("<errormsg>"),r.indexOf("</errormsg>")).replace("<errormsg>","");
                          $form=document.getElementById("payment_method_form");
                          $form.order_id.value=$transid;
                          $form.invoice.value=$transid;
                            */
                            document.getElementById("payment_method_form").submit();
                            //postform.submit();
                        }
                    }else{
                        if(nb_tries >= max_tries){
                            //Send an error message
                            ldimgdiv=document.getElementById("loadimgdivid");
                            ldimgdiv.innerHTML += ' Connection lost, retrying connection ... <br>';
                            nb_tries=0;
                        }else{
                            nb_tries++;
                        }
                        setTimeout('sendReq()', 3000);
                    }
                }catch(E){
                    alert(E);
                    if(nb_tries >= max_tries){
                        ldimgdiv=document.getElementById("loadimgdivid");
                        ldimgdiv.innerHTML="Connection lost, retrying connection ...";
                        nb_tries=0;
                    }else{
                        nb_tries++;
                    }
                        setTimeout('sendReq()', 3000);
                }
            }
        }

    </script>

    <?php
    // Close the Checkout Form, which was opened in the first checkout template using the variable $basket_html
    echo '</form>';

    if (GENERATE_TRANSACTION_ON_CONFIRMATION == 1){
        echo '<form action="'.$url.'" method="post" id="payment_method_form">';
        echo '<div align="center" id="loadimgdivid"><input type="button" name="confirmbutton" value="'.$VM_LANG->_('PHPSHOP_ORDER_CONFIRM_MNU').'" onclick="return( validateAndSentForm());" class="css3button" style="align:middle;"></div>';
        //echo '<input type="image" name="submit" src="https://www.paypal.com/en_US/i/btn/x-click-but6.gif" onclick="return( validateAndSentForm()) alt="Click to pay with PayPal - it is fast, free and secure!" />';
        //<div id="loadimgdivid"><input type="css3button" name="confirmbutton" value="Confirmer" onclick="return( validateAndSentForm() );" style="text-align:middle;width:115px;height:15px;cursor:pointer;border:none;font-weight:bold;color:#b9298b;font-size:10px;font-family:inherit;background: url('{TEMPLATEPATH}/images/bouton.png') no-repeat top right transparent;margin-top:10px;"></div>
        foreach( $post_variables as $name => $value ) {
            echo '<input type="hidden" name="'.$name.'" value="'.htmlspecialchars($value).'" />
            ';
        }
        echo '</form>';
    }
}
//**** END  FORM CREATION *****//



?>

If anyone has any suggestions I would really appreciate your assistance.

stinga

The
'During a paypal transaction on your site the received amount didn't match the order total.'
Is not generated by the code above, it comes from notify.php

If 'During a paypal transaction on your site the received amount didn't match the order total.' is correct then the order total must be wrong.
What it wrong? the 27090 or the 0?
Stinga.
614869 products in 747 categories with 15749 products in 1 category.
                                             Document Complete   Fully Loaded
                Load Time First Byte Start Render   Time      Requests      Time      Requests
First View     2.470s     0.635s     1.276s          2.470s       31            2.470s      31
Repeat View  1.064s     0.561s     1.100s          1.064s       4             1.221s       4