/** * Get zen-cart order totals. * * @param ShoppingCart $shoppingCart The current shopping cart. * @return array zencart order totals. */ protected function getZenTotals(ShoppingCart $shoppingCart) { global $order, $shipping_modules; // save $otmp = $order; $smtmp = $shipping_modules; $order = new \order(); if (!isset($shipping_modules)) { $ssm = array(); if (null != ($shippingMethod = $shoppingCart->getSelectedShippingMethod())) { $ssm = array('id' => $shippingMethod->getShippingId(), 'title' => $shippingMethod->getName(), 'cost' => $shippingMethod->getCost()); } $shipping_modules = new \shipping($ssm); } $zenTotals = new \order_total(); $zenTotals->collect_posts(); $zenTotals->pre_confirmation_check(); $zenTotals->process(); // restore $order = $otmp; $shipping_modules = $smtmp; return $zenTotals; }
} if ($kein_versand == 1) { $_SESSION['shipping'] = false; } $order = new order(); // load all enabled payment modules require DIR_WS_CLASSES . 'payment.php'; $payment_modules = new payment($_SESSION['payment']); $payment_modules->update_status(); require DIR_WS_CLASSES . 'order_total.php'; // GV Code ICW ADDED FOR CREDIT CLASS SYSTEM $order_total_modules = new order_total(); $order_total_modules->process(); // GV Code Start $order_total_modules->collect_posts(); $order_total_modules->pre_confirmation_check(); // GV Code End if (is_array($payment_modules->modules)) { $payment_modules->pre_confirmation_check(); } $breadcrumb->add(NAVBAR_TITLE_PAYPAL_CHECKOUT, xtc_href_link(FILENAME_PAYPAL_CHECKOUT, '', 'SSL')); require DIR_WS_INCLUDES . 'header.php'; if (SHOW_IP_LOG == 'true') { $smarty->assign('IP_LOG', 'true'); if ($_SERVER['HTTP_X_FORWARDED_FOR']) { $customers_ip = $_SERVER['HTTP_X_FORWARDED_FOR']; } else { $customers_ip = $_SERVER['REMOTE_ADDR']; } $smarty->assign('CUSTOMERS_IP', $customers_ip); }
/** * This method sends the user to PayPal's site * There, they will log in to their account, choose a funding source and shipping method * and then return to our site with an EC token */ function ec_step1() { global $order, $db, $doPayPal; // if cart is empty due to timeout on login or shopping cart page, go to timeout screen if ($_SESSION['cart']->count_contents() == 0) { zen_redirect(zen_href_link(FILENAME_TIME_OUT, '', 'SSL')); } // init new order object require DIR_WS_CLASSES . 'order.php'; $order = new order(); // load the selected shipping module so that shipping taxes can be assessed require DIR_WS_CLASSES . 'shipping.php'; $shipping_modules = new shipping($_SESSION['shipping']); // load OT modules so that discounts and taxes can be assessed require DIR_WS_CLASSES . 'order_total.php'; $order_total_modules = new order_total(); $order_totals = $order_total_modules->pre_confirmation_check(); $order_totals = $order_total_modules->process(); $doPayPal = $this->paypal_init(); $options = array(); // unused at present: // $options['CUSTOM'] = ''; // $options['INVNUM'] = ''; // Determine the language to use when visiting the PP site $lc_code = $this->getLanguageCode(); if ($lc_code != '') { $options['LOCALECODE'] = $lc_code; } // Set currency and amount $options['CURRENCY'] = $this->selectCurrency(); $order_amount = $this->calc_order_amount($order->info['total'], $options['CURRENCY']); // Payment Transaction/Authorization Mode $options['PAYMENTACTION'] = MODULE_PAYMENT_PAYPALWPP_TRANSACTION_MODE == 'Auth Only' ? 'Authorization' : 'Sale'; // for future: if (MODULE_PAYMENT_PAYPALWPP_TRANSACTION_MODE == 'Order') { $options['PAYMENTACTION'] = 'Order'; } // Set the return URL if they click "Submit" on PayPal site $return_url = zen_href_link('ipn_main_handler.php', 'type=ec', 'SSL', true, true, true); // Select the return URL if they click "cancel" on PayPal site or click to return without making payment or login $cancel_url = zen_href_link($_SESSION['customer_first_name'] != '' && $_SESSION['customer_id'] != '' ? FILENAME_CHECKOUT_SHIPPING : FILENAME_LOGIN, 'ec_cancel=1', 'SSL'); // debug $this->zcLog('ec_step1 - 1', 'Checking to see if we are in markflow' . "\n" . 'cart contents: ' . $_SESSION['cart']->get_content_type() . "\n\nNOTE: " . '$this->showPaymentPage = ' . (int) $this->showPaymentPage . "\nCustomer ID: " . (int) $_SESSION['customer_id'] . "\nSession Data: " . print_r($_SESSION, true)); /** * Check whether shipping is required on this order or not. * If not, tell PayPal to skip all shipping options * ie: don't ask for any shipping info if cart content is strictly virtual and customer is already logged-in * (if not logged in, we need address information only to build the customer record) */ if ($_SESSION['cart']->get_content_type() == 'virtual' && isset($_SESSION['customer_id']) && $_SESSION['customer_id'] > 0) { $this->zcLog('ec-step1-addr_check', "cart contents is virtual and customer is logged in ... therefore options['NOSHIPPING']=1"); $options['NOSHIPPING'] = 1; } else { $this->zcLog('ec-step1-addr_check', "cart contents is not all virtual or customer is not logged in ... therefore will be submitting address details"); // If we are in a "mark" flow and the customer has a usable address, set the addressoverride variable to 1. This will // override the shipping address in PayPal with the shipping address that is selected in Zen Cart. if (($address_arr = $this->getOverrideAddress()) !== false) { $address_error = false; foreach (array('entry_firstname', 'entry_lastname', 'entry_street_address', 'entry_city', 'entry_postcode', 'zone_code', 'countries_iso_code_2') as $key) { if ($address_arr[$key] == '') { $address_error = true; } if ($address_error == true) { $this->zcLog('ec-step1-addr_check2', '$address_error = true because ' . $key . ' is blank.'); } } if ($address_error == false) { // set the override var $options['ADDROVERRIDE'] = 1; // set the address info $options['SHIPTONAME'] = $address_arr['entry_firstname'] . ' ' . $address_arr['entry_lastname']; $options['SHIPTOSTREET'] = $address_arr['entry_street_address']; if ($address_arr['entry_suburb'] != '') { $options['SHIPTOSTREET2'] = $address_arr['entry_suburb']; } $options['SHIPTOCITY'] = $address_arr['entry_city']; $options['SHIPTOZIP'] = $address_arr['entry_postcode']; $options['SHIPTOSTATE'] = $address_arr['zone_code']; $options['SHIPTOCOUNTRYCODE'] = $address_arr['countries_iso_code_2']; } } $this->zcLog('ec-step1-addr_check3', 'address details from override check:' . print_r($address_arr, true)); // Do we require a "confirmed" shipping address ? if (MODULE_PAYMENT_PAYPALWPP_CONFIRMED_ADDRESS == 'Yes') { $options['REQCONFIRMSHIPPING'] = 1; } } // if we know customer's email address, supply it, so as to pre-fill the signup box at PayPal (for new PayPal accounts only) if (!empty($_SESSION['customer_first_name']) && !empty($_SESSION['customer_id'])) { $sql = "select * from " . TABLE_CUSTOMERS . " where customers_id = :custID "; $sql = $db->bindVars($sql, ':custID', $_SESSION['customer_id'], 'integer'); $zc_getemail = $db->Execute($sql); if ($zc_getemail->RecordCount() > 0 && $zc_getemail->fields['customers_email_address'] != '') { $options['EMAIL'] = $zc_getemail->fields['customers_email_address']; } if ($zc_getemail->RecordCount() > 0 && $zc_getemail->fields['customers_telephone'] != '') { $options['PHONENUM'] = $zc_getemail->fields['customers_telephone']; } } // alter PayPal login page: $options['SOLUTIONTYPE'] = 'SOLE'; // debug $this->zcLog('ec_step1 - 2 -submit', print_r(array_merge(array('AMT' => number_format($order_amount, 2), 'RETURNURL' => $return_url, 'CANCELURL' => $cancel_url), $options), true)); /** * Ask PayPal for the token with which to initiate communications */ $response = $doPayPal->SetExpressCheckout(number_format($order_amount, 2), $return_url, $cancel_url, $options); /** * Determine result of request for token -- if error occurred, the errorHandler will redirect accordingly */ $error = $this->_errorHandler($response, 'SetExpressCheckout'); // Success, so read the EC token $_SESSION['paypal_ec_token'] = preg_replace('/[^0-9.A-Z\\-]/', '', urldecode($response['TOKEN'])); // prepare to redirect to PayPal so the customer can log in and make their selections $paypal_url = $this->getPayPalLoginServer(); // Set the name of the displayed "continue" button on the PayPal site. // 'commit' = "Pay Now" || 'continue' = "Review Payment" $orderReview = true; if ($_SESSION['paypal_ec_markflow'] == 1) { $orderReview = false; } $userActionKey = "&useraction=" . ((int) $orderReview == false ? 'commit' : 'continue'); // This is where we actually redirect the customer's browser to PayPal. Upon return, they go to ec_step2 header("HTTP/1.1 302 Object Moved"); zen_redirect($paypal_url . "?cmd=_express-checkout&token=" . $_SESSION['paypal_ec_token'] . $userActionKey); }
$oOrder = new order; if ( (isset($_SESSION['shipping'])) && ($_SESSION['shipping']['id'] == 'free_free')) { if ( ($oOrder->info['total'] - $oOrder->info['shipping_cost']) < MODULE_ORDER_TOTAL_SHIPPING_FREE_SHIPPING_OVER ) { MyOOS_CoreApi::redirect(oos_href_link($aPages['checkout_shipping'], '', 'SSL')); } } $oPaymentModules->update_status(); $oOrderTotalModules = new order_total; $oOrderTotalModules->collect_posts(); if (isset($_SESSION['cot_gv'])) { $credit_covers = $oOrderTotalModules->pre_confirmation_check(); } if ( (is_array($oPaymentModules->modules)) && (count($oPaymentModules->modules) > 1) && (!is_object($$_SESSION['payment'])) && (!$credit_covers) ) { $_SESSION['error_message'] = $aLang['error_no_payment_module_selected']; MyOOS_CoreApi::redirect(oos_href_link($aPages['checkout_payment'], '', 'SSL')); } if (is_array($oPaymentModules->modules)) { $oPaymentModules->pre_confirmation_check(); } // load the selected shipping module require 'includes/classes/class_shipping.php'; $shipping_modules = new shipping($_SESSION['shipping']);
/** * This method sends the customer to PayPal's site * There, they will log in to their PayPal account, choose a funding source and shipping method * and then return to our store site with an EC token */ function ec_step1() { global $order, $order_totals, $db, $doPayPal; // if cart is empty due to timeout on login or shopping cart page, go to timeout screen if ($_SESSION['cart']->count_contents() == 0) { $message = 'Logging out due to empty shopping cart. Is session started properly? ... ' . "\nSESSION Details:\n" . print_r($_SESSION, TRUE) . 'GET:' . "\n" . print_r($_GET, TRUE); include_once DIR_WS_MODULES . 'payment/paypal/paypal_functions.php'; ipn_debug_email($message); zen_redirect(zen_href_link(FILENAME_TIME_OUT, '', 'SSL')); } // init new order object require DIR_WS_CLASSES . 'order.php'; $order = new order(); // load the selected shipping module so that shipping taxes can be assessed require DIR_WS_CLASSES . 'shipping.php'; $shipping_modules = new shipping($_SESSION['shipping']); // load OT modules so that discounts and taxes can be assessed require DIR_WS_CLASSES . 'order_total.php'; $order_total_modules = new order_total(); $order_totals = $order_total_modules->pre_confirmation_check(); $order_totals = $order_total_modules->process(); $doPayPal = $this->paypal_init(); $options = array(); $options = $this->getLineItemDetails($this->selectCurrency()); // Determine the language to use when visiting the PP site $lc_code = $this->getLanguageCode(); if ($lc_code != '') { $options['LOCALECODE'] = $lc_code; } // Set currency and amount $options['CURRENCY'] = $this->selectCurrency(); $order_amount = $this->calc_order_amount($order->info['total'], $options['CURRENCY']); // Payment Transaction/Authorization Mode $options['PAYMENTACTION'] = MODULE_PAYMENT_PAYPALWPP_TRANSACTION_MODE == 'Auth Only' ? 'Authorization' : 'Sale'; // for future: if (MODULE_PAYMENT_PAYPALWPP_TRANSACTION_MODE == 'Order') { $options['PAYMENTACTION'] = 'Order'; } $options['ALLOWNOTE'] = 1; // allow customer to enter a note on the PayPal site, which will be copied to order comments upon return to store. $options['SOLUTIONTYPE'] = 'Sole'; // Use 'Mark' for normal Express Checkout, 'Sole' for auctions or alternate flow $options['LANDINGPAGE'] = 'Billing'; // "Billing" or "Login" selects the style of landing page on PayPal site during checkout // Set the return URL if they click "Submit" on PayPal site $return_url = str_replace('&', '&', zen_href_link('ipn_main_handler.php', 'type=ec', 'SSL', true, true, true)); // Select the return URL if they click "cancel" on PayPal site or click to return without making payment or login $cancel_url = str_replace('&', '&', zen_href_link($_SESSION['customer_first_name'] != '' && $_SESSION['customer_id'] != '' ? FILENAME_CHECKOUT_SHIPPING : FILENAME_SHOPPING_CART, 'ec_cancel=1', 'SSL')); // debug $val = $_SESSION; unset($val['navigation']); $this->zcLog('ec_step1 - 1', 'Checking to see if we are in markflow' . "\n" . 'cart contents: ' . $_SESSION['cart']->get_content_type() . "\n\nNOTE: " . '$this->showPaymentPage = ' . (int) $this->showPaymentPage . "\nCustomer ID: " . (int) $_SESSION['customer_id'] . "\nSession Data: " . print_r($val, true)); /** * Check whether shipping is required on this order or not. * If not, tell PayPal to skip all shipping options * ie: don't ask for any shipping info if cart content is strictly virtual and customer is already logged-in * (if not logged in, we need address information only to build the customer record) */ if ($_SESSION['cart']->get_content_type() == 'virtual' && isset($_SESSION['customer_id']) && $_SESSION['customer_id'] > 0) { $this->zcLog('ec-step1-addr_check', "cart contents is virtual and customer is logged in ... therefore options['NOSHIPPING']=1"); $options['NOSHIPPING'] = 1; } else { $this->zcLog('ec-step1-addr_check', "cart content is not all virtual (or customer is not logged in) ... therefore will be submitting address details"); // If we are in a "mark" flow and the customer has a usable address, set the addressoverride variable to 1. This will // override the shipping address in PayPal with the shipping address that is selected in Zen Cart. // @TODO: consider using address-validation against Paypal's addresses if (($address_arr = $this->getOverrideAddress()) !== false) { $address_error = false; foreach (array('entry_firstname', 'entry_lastname', 'entry_street_address', 'entry_city', 'entry_postcode', 'zone_code', 'countries_iso_code_2') as $val) { if ($address_arr[$val] == '') { $address_error = true; } if ($address_error == true) { $this->zcLog('ec-step1-addr_check2', '$address_error = true because ' . $val . ' is blank.'); } } if ($address_error == false) { // set the override var $options['ADDROVERRIDE'] = 1; // set the address info $options['SHIPTONAME'] = $address_arr['entry_firstname'] . ' ' . $address_arr['entry_lastname']; $options['SHIPTOSTREET'] = $address_arr['entry_street_address']; if ($address_arr['entry_suburb'] != '') { $options['SHIPTOSTREET2'] = $address_arr['entry_suburb']; } $options['SHIPTOCITY'] = $address_arr['entry_city']; $options['SHIPTOZIP'] = $address_arr['entry_postcode']; $options['SHIPTOSTATE'] = $address_arr['zone_code']; $options['SHIPTOCOUNTRYCODE'] = $address_arr['countries_iso_code_2']; } } $this->zcLog('ec-step1-addr_check3', 'address details from override check:' . ($address_arr == FALSE ? ' <NONE FOUND>' : print_r($address_arr, true))); // Do we require a "confirmed" shipping address ? if (MODULE_PAYMENT_PAYPALWPP_CONFIRMED_ADDRESS == 'Yes') { $options['REQCONFIRMSHIPPING'] = 1; } } // if we know customer's email address, supply it, so as to pre-fill the signup box at PayPal (useful for new PayPal accounts only) if (!empty($_SESSION['customer_first_name']) && !empty($_SESSION['customer_id'])) { $sql = "select * from " . TABLE_CUSTOMERS . " where customers_id = :custID "; $sql = $db->bindVars($sql, ':custID', $_SESSION['customer_id'], 'integer'); $zc_getemail = $db->Execute($sql); if ($zc_getemail->RecordCount() > 0 && $zc_getemail->fields['customers_email_address'] != '') { $options['EMAIL'] = $zc_getemail->fields['customers_email_address']; } if ($zc_getemail->RecordCount() > 0 && $zc_getemail->fields['customers_telephone'] != '') { $options['SHIPTOPHONENUM'] = $zc_getemail->fields['customers_telephone']; } } if (!isset($options['AMT'])) { $options['AMT'] = number_format($order_amount, 2); } $this->zcLog('ec_step1 - 2 -submit', print_r(array_merge($options, array('RETURNURL' => $return_url, 'CANCELURL' => $cancel_url)), true)); /** * Ask PayPal for the token with which to initiate communications */ $response = $doPayPal->SetExpressCheckout($return_url, $cancel_url, $options); $submissionCheckOne = TRUE; $submissionCheckTwo = TRUE; if ($submissionCheckOne) { // If there's an error on line-item details, remove tax values and resubmit, since the most common cause of 10413 is tax mismatches if ($response['L_ERRORCODE0'] == '10413') { $this->zcLog('ec_step1 - 3 - removing tax portion', 'Tax Subtotal does not match sum of taxes for line-items. Tax details removed from line-item submission data.' . "\n" . print_r($options, true)); //echo '1st submission REJECTED. {'.$response['L_ERRORCODE0'].'}<pre>'.print_r($options, true) . urldecode(print_r($response, true)); $tsubtotal = 0; foreach ($options as $key => $value) { if (substr($key, 0, 8) == 'L_TAXAMT') { $tsubtotal += preg_replace('/[^0-9.\\-]/', '', $value); unset($options[$key]); } } $options['TAXAMT'] = $tsubtotal; $amt = preg_replace('/[^0-9.%]/', '', $options['AMT']); // echo 'oldAMT:'.$amt; // echo ' newTAXAMT:'.$tsubtotal; $taxamt = preg_replace('/[^0-9.%]/', '', $options['TAXAMT']); $shipamt = preg_replace('/[^0-9.%]/', '', $options['SHIPPINGAMT']); $itemamt = preg_replace('/[^0-9.%]/', '', $options['ITEMAMT']); $calculatedAmount = $itemamt + $taxamt + $shipamt; if ($amt != $calculatedAmount) { $amt = $calculatedAmount; } // echo ' newAMT:'.$amt; $options['AMT'] = $amt; $response = $doPayPal->SetExpressCheckout($return_url, $cancel_url, $options); //echo '<br>2nd submission. {'.$response['L_ERRORCODE0'].'}<pre>'.print_r($options, true); } if ($submissionCheckTwo) { if ($response['L_ERRORCODE0'] == '10413') { $this->zcLog('ec_step1 - 4 - removing line-item details', 'PayPal designed their own mathematics rules. Dumbing it down for them.' . "\n" . print_r($options, true)); //echo '2nd submission REJECTED. {'.$response['L_ERRORCODE0'].'}<pre>'.print_r($options, true) . urldecode(print_r($response, true)); foreach ($options as $key => $value) { if (substr($key, 0, 2) == 'L_') { unset($options[$key]); } } $amt = preg_replace('/[^0-9.%]/', '', $options['AMT']); $taxamt = preg_replace('/[^0-9.%]/', '', $options['TAXAMT']); $shipamt = preg_replace('/[^0-9.%]/', '', $options['SHIPPINGAMT']); $itemamt = preg_replace('/[^0-9.%]/', '', $options['ITEMAMT']); $calculatedAmount = $itemamt + $taxamt + $shipamt; if ($amt != $calculatedAmount) { $amt = $calculatedAmount; } $options['AMT'] = $amt; $response = $doPayPal->SetExpressCheckout($return_url, $cancel_url, $options); //echo '<br>3rd submission. {'.$response['L_ERRORCODE0'].'}<pre>'.print_r($options, true); } } } /** * Determine result of request for token -- if error occurred, the errorHandler will redirect accordingly */ $error = $this->_errorHandler($response, 'SetExpressCheckout'); // Success, so read the EC token $_SESSION['paypal_ec_token'] = preg_replace('/[^0-9.A-Z\\-]/', '', urldecode($response['TOKEN'])); // prepare to redirect to PayPal so the customer can log in and make their selections $paypal_url = $this->getPayPalLoginServer(); // Set the name of the displayed "continue" button on the PayPal site. // 'commit' = "Pay Now" || 'continue' = "Review Payment" $orderReview = true; if ($_SESSION['paypal_ec_markflow'] == 1) { $orderReview = false; } $userActionKey = "&useraction=" . ((int) $orderReview == false ? 'commit' : 'continue'); // This is where we actually redirect the customer's browser to PayPal. Upon return from PayPal, they go to ec_step2 header("HTTP/1.1 302 Object Moved"); zen_redirect($paypal_url . "?cmd=_express-checkout&token=" . $_SESSION['paypal_ec_token'] . $userActionKey); // this should never be reached: return $error; }
/** * This method is for step 2 of the express checkout option. * This * retrieves from PayPal the data set by step one and sets the Zen Cart * data accordingly depending on admin settings. */ function ec_step2() { // Visitor just came back from PayPal and so we collect all // the info returned, create an account if necessary, then log // them in, and then send them to the appropriate page. if (empty($_SESSION['paypal_ec_token'])) { // see if the token is set -- if not, we cannot continue -- ideally the token should match the session token if (isset($_GET['token'])) { // we have a token, so we will proceed $_SESSION['paypal_ec_token'] = $_GET['token']; // sanitize this $_SESSION['paypal_ec_token'] = preg_replace('/[^0-9.A-Z\\-]/', '', $_GET['token']); } else { // no token -- not ready for this step -- send them back to checkout page with error $this->terminateEC(MODULE_PAYMENT_PAYPALWPP_INVALID_RESPONSE, true); } } // debug // $this->zcLog('PayPal test Log - ec_step2 $_REQUEST data', "In function: ec_step2()\r\nData in \$_REQUEST = \r\n" . print_r($_REQUEST, true)); // Initialize the paypal caller object. global $doPayPal; $doPayPal = $this->paypal_init(); // with the token we retrieve the data about this user $response = $doPayPal->GetExpressCheckoutDetails($_SESSION['paypal_ec_token']); // $this->zcLog('ec_step2 - GetExpressCheckout response', print_r($response, true)); /** * Determine result of request for data -- if error occurred, the errorHandler will redirect accordingly */ $error = $this->_errorHandler($response, 'GetExpressCheckoutDetails'); // Check for blank address -- if address received from PayPal is blank, ask the customer to register in the store first and then resume checkout if ($_SESSION['cart']->get_content_type() != 'virtual') { if ($response['SHIPTONAME'] . $response['SHIPTOSTREET'] . $response['SHIPTOSTREET2'] . $response['SHIPTOCITY'] . $response['SHIPTOSTATE'] . $response['SHIPTOZIP'] . $response['SHIPTOCOUNTRYCODE'] == '') { $this->terminateEC(MODULES_PAYMENT_PAYPALWPP_TEXT_BLANK_ADDRESS, true, FILENAME_CREATE_ACCOUNT); } } // will we be creating an account for this customer? We must if the cart contents are virtual, so can login to download etc. if ($_SESSION['cart']->get_content_type('true') > 0 || in_array($_SESSION['cart']->content_type, array('mixed', 'virtual'))) { $this->new_acct_notify = 'Yes'; } // get the payer_id from the customer's info as returned from PayPal $_SESSION['paypal_ec_payer_id'] = $response['PAYERID']; $this->notify('NOTIFY_PAYPAL_EXPRESS_CHECKOUT_PAYERID_DETERMINED', $response['PAYERID']); $gender = ''; if (urldecode($response['SALUTATION'] == 'Mr')) { $gender = 'm'; } if (in_array(urldecode($response['SALUTATION']), array('Ms', 'Mrs'))) { $gender = 'f'; } // prepare the information to pass to the ec_step2_finish() function, which does the account creation, address build, etc $step2_payerinfo = array('payer_id' => $response['PAYERID'], 'payer_email' => urldecode($response['EMAIL']), 'payer_salutation' => urldecode($response['SALUTATION']), 'payer_gender' => $gender, 'payer_firstname' => urldecode($response['FIRSTNAME']), 'payer_lastname' => urldecode($response['LASTNAME']), 'payer_business' => urldecode($response['BUSINESS']), 'payer_status' => $response['PAYERSTATUS'], 'ship_country_code' => urldecode($response['COUNTRYCODE']), 'ship_address_status' => urldecode($response['ADDRESSSTATUS']), 'ship_phone' => urldecode($response['SHIPTOPHONENUM'] != '' ? $response['SHIPTOPHONENUM'] : $response['PHONENUM']), 'order_comment' => urldecode($response['NOTETEXT'])); // if (strtoupper($response['ADDRESSSTATUS']) == 'NONE' || !isset($response['SHIPTOSTREET']) || $response['SHIPTOSTREET'] == '') { // $step2_shipto = array(); // } else { // accomodate PayPal bug which repeats 1st line of address for 2nd line if 2nd line is empty. if ($response['SHIPTOSTREET2'] == $response['SHIPTOSTREET1']) { $response['SHIPTOSTREET2'] = ''; } // accomodate PayPal bug which incorrectly treats 'Yukon Territory' as YK instead of ISO standard of YT. if ($response['SHIPTOSTATE'] == 'YK') { $response['SHIPTOSTATE'] = 'YT'; } // same with Newfoundland if ($response['SHIPTOSTATE'] == 'NF') { $response['SHIPTOSTATE'] = 'NL'; } // process address details supplied $step2_shipto = array('ship_name' => urldecode($response['SHIPTONAME']), 'ship_street_1' => urldecode($response['SHIPTOSTREET']), 'ship_street_2' => urldecode($response['SHIPTOSTREET2']), 'ship_city' => urldecode($response['SHIPTOCITY']), 'ship_state' => isset($response['SHIPTOSTATE']) && $response['SHIPTOSTATE'] != '' ? urldecode($response['SHIPTOSTATE']) : urldecode($response['SHIPTOCITY']), 'ship_postal_code' => urldecode($response['SHIPTOZIP']), 'ship_country_code' => urldecode($response['SHIPTOCOUNTRYCODE']), 'ship_country_name' => isset($response['SHIPTOCOUNTRY']) ? urldecode($response['SHIPTOCOUNTRY']) : urldecode($response['SHIPTOCOUNTRYNAME'])); // } // reset all previously-selected shipping choices, because cart contents may have been changed if (!(isset($_SESSION['paypal_ec_markflow']) && $_SESSION['paypal_ec_markflow'] == 1)) { unset($_SESSION['shipping']); } // set total temporarily based on amount returned from PayPal, so validations continue to work properly global $order, $order_totals; if (!isset($order) || !isset($order->info) || !is_array($order->info) || !zen_not_null($order)) { $this->zcLog('ec_step2 ', 'Re-instantiating $order object.'); // init new order object if (!class_exists('order')) { require DIR_WS_CLASSES . 'order.php'; } $order = new order(); // load the selected shipping module so that shipping taxes can be assessed if (!class_exists('shipping')) { require DIR_WS_CLASSES . 'shipping.php'; } $shipping_modules = new shipping($_SESSION['shipping']); // load OT modules so that discounts and taxes can be assessed if (!class_exists('order_total')) { require DIR_WS_CLASSES . 'order_total.php'; } $order_total_modules = new order_total(); $order_totals = $order_total_modules->pre_confirmation_check(); $order_totals = $order_total_modules->process(); $this->zcLog('ec_step2 ', 'Instantiated $order object contents: ' . print_r($order, true)); } $order->info['total'] = urldecode($response['AMT']); // $this->zcLog('ec_step2 - processed info', print_r(array_merge($step2_payerinfo, $step2_shipto), true)); // send data off to build account, log in, set addresses, place order $this->ec_step2_finish(array_merge($step2_payerinfo, $step2_shipto), $this->new_acct_notify); }
public function prepareConfirmation() { global $messageStack, $template, $breadcrumb, $template_dir_select, $template_dir, $language_page_directory, $currencies, $order, $zco_notifier, $db, $current_page_base, $order_total_modules, $credit_covers; // error_reporting(E_ALL); // ini_set('display_errors', 'on'); $_GET['main_page'] = $current_page_base = $current_page = FILENAME_CHECKOUT_CONFIRMATION; if ($_SESSION['cart']->count_contents() <= 0) { zen_redirect(zen_href_link(FILENAME_TIME_OUT)); } if (!$_SESSION['customer_id']) { $_SESSION['navigation']->set_snapshot(array('mode' => 'SSL', 'page' => FILENAME_CHECKOUT_PAYMENT)); zen_redirect(zen_href_link(FILENAME_LOGIN, '', 'SSL')); } else { // validate customer if (zen_get_customer_validate_session($_SESSION['customer_id']) == false) { $_SESSION['navigation']->set_snapshot(); zen_redirect(zen_href_link(FILENAME_LOGIN, '', 'SSL')); } } // avoid hack attempts during the checkout procedure by checking the internal cartID if (isset($_SESSION['cart']->cartID) && $_SESSION['cartID']) { if ($_SESSION['cart']->cartID != $_SESSION['cartID']) { zen_redirect(zen_href_link(FILENAME_CHECKOUT_SHIPPING, '', 'SSL')); } } // if no shipping method has been selected, redirect the customer to the shipping method selection page if (!isset($_SESSION['shipping'])) { zen_redirect(zen_href_link(FILENAME_CHECKOUT_SHIPPING, '', 'SSL')); } if (isset($_SESSION['shipping']['id']) && $_SESSION['shipping']['id'] == 'free_free' && $_SESSION['cart']->get_content_type() != 'virtual' && defined('MODULE_ORDER_TOTAL_SHIPPING_FREE_SHIPPING') && MODULE_ORDER_TOTAL_SHIPPING_FREE_SHIPPING == 'true' && defined('MODULE_ORDER_TOTAL_SHIPPING_FREE_SHIPPING_OVER') && $_SESSION['cart']->show_total() < MODULE_ORDER_TOTAL_SHIPPING_FREE_SHIPPING_OVER) { zen_redirect(zen_href_link(FILENAME_CHECKOUT_SHIPPING, '', 'SSL')); } if (isset($_POST['payment'])) { $_SESSION['payment'] = $_POST['payment']; } $_SESSION['comments'] = $_POST['comments']; if (DISPLAY_CONDITIONS_ON_CHECKOUT == 'true') { if (!isset($_POST['conditions']) || $_POST['conditions'] != '1') { $messageStack->add_session('checkout_payment', ERROR_CONDITIONS_NOT_ACCEPTED, 'error'); } } // echo $messageStack->size('checkout_payment'); // load the selected payment module require DIR_WS_CLASSES . 'payment.php'; $payment_modules = new payment($_POST['payment']); $payment_modules->update_status(); if (($_POST['payment'] == '' || !is_object($payment_modules->paymentClass)) && $credit_covers === FALSE) { $messageStack->add_session('checkout_payment', ERROR_NO_PAYMENT_MODULE_SELECTED, 'error'); } $GLOBALS[$_POST['payment']] = $payment_modules->paymentClass; require DIR_WS_CLASSES . 'order.php'; $order = new order(); // load the selected shipping module require DIR_WS_CLASSES . 'shipping.php'; $shipping_modules = new shipping($_SESSION['shipping']); require DIR_WS_CLASSES . 'order_total.php'; $order_total_modules = new order_total(); $order_total_modules->collect_posts(); $order_total_modules->pre_confirmation_check(); if (!isset($credit_covers)) { $credit_covers = FALSE; } // echo 'credit covers'.$credit_covers; if ($credit_covers) { unset($_SESSION['payment']); $_SESSION['payment'] = ''; } // @debug echo ($credit_covers == true) ? 'TRUE' : 'FALSE'; if (is_array($payment_modules->modules)) { $payment_modules->pre_confirmation_check(); } if ($messageStack->size('checkout_payment') > 0) { zen_redirect(zen_href_link(FILENAME_CHECKOUT_PAYMENT, '', 'SSL')); } // Stock Check $flagAnyOutOfStock = false; $stock_check = array(); if (STOCK_CHECK == 'true') { for ($i = 0, $n = sizeof($order->products); $i < $n; $i++) { if ($stock_check[$i] = zen_check_stock($order->products[$i]['id'], $order->products[$i]['qty'])) { $flagAnyOutOfStock = true; } } // Out of Stock if (STOCK_ALLOW_CHECKOUT != 'true' && $flagAnyOutOfStock == true) { zen_redirect(zen_href_link(FILENAME_SHOPPING_CART)); } } // update customers_referral with $_SESSION['gv_id'] if ($_SESSION['cc_id']) { $discount_coupon_query = "SELECT coupon_code\n FROM " . TABLE_COUPONS . "\n WHERE coupon_id = :couponID"; $discount_coupon_query = $db->bindVars($discount_coupon_query, ':couponID', $_SESSION['cc_id'], 'integer'); $discount_coupon = $db->Execute($discount_coupon_query); $customers_referral_query = "SELECT customers_referral\n FROM " . TABLE_CUSTOMERS . "\n WHERE customers_id = :customersID"; $customers_referral_query = $db->bindVars($customers_referral_query, ':customersID', $_SESSION['customer_id'], 'integer'); $customers_referral = $db->Execute($customers_referral_query); // only use discount coupon if set by coupon if ($customers_referral->fields['customers_referral'] == '' and CUSTOMERS_REFERRAL_STATUS == 1) { $sql = "UPDATE " . TABLE_CUSTOMERS . "\n SET customers_referral = :customersReferral\n WHERE customers_id = :customersID"; $sql = $db->bindVars($sql, ':customersID', $_SESSION['customer_id'], 'integer'); $sql = $db->bindVars($sql, ':customersReferral', $discount_coupon->fields['coupon_code'], 'string'); $db->Execute($sql); } else { // do not update referral was added before } } if (isset(${$_SESSION}['payment']->form_action_url)) { $form_action_url = ${$_SESSION}['payment']->form_action_url; } else { $form_action_url = zen_href_link(FILENAME_CHECKOUT_PROCESS, '', 'SSL'); } // if shipping-edit button should be overridden, do so $editShippingButtonLink = zen_href_link(FILENAME_CHECKOUT_SHIPPING, '', 'SSL'); if (method_exists(${$_SESSION}['payment'], 'alterShippingEditButton')) { $theLink = ${$_SESSION}['payment']->alterShippingEditButton(); if ($theLink) { $editShippingButtonLink = $theLink; } } // deal with billing address edit button $flagDisablePaymentAddressChange = false; if (isset(${$_SESSION}['payment']->flagDisablePaymentAddressChange)) { $flagDisablePaymentAddressChange = ${$_SESSION}['payment']->flagDisablePaymentAddressChange; } $current_page_base = FILENAME_CHECKOUT_CONFIRMATION; require_once DIR_WS_LANGUAGES . $_SESSION['language'] . '.php'; require_once DIR_WS_MODULES . zen_get_module_directory('require_languages.php'); require_once DIR_WS_MODULES . zen_get_module_directory('meta_tags.php'); $breadcrumb->add(NAVBAR_TITLE_1, zen_href_link(FILENAME_CHECKOUT_SHIPPING, '', 'SSL')); $breadcrumb->add(NAVBAR_TITLE_2); $breadCrumbHtml = $breadcrumb->trail(BREAD_CRUMBS_SEPARATOR); $body_code = DIR_FS_CATALOG . $template->get_template_dir('tpl_ajax_checkout_confirmation_default.php', DIR_WS_TEMPLATE, $current_page_base, 'templates') . '/tpl_ajax_checkout_confirmation_default.php'; ob_start(); require_once $body_code; $confirmationHtml = ob_get_clean(); ob_flush(); return array('breadCrumbHtml' => $breadCrumbHtml, 'confirmationHtml' => $confirmationHtml, 'pageTitle' => META_TAG_TITLE); }
/** * Assert info. * * @param boolean withTotals Flag to include/apply totals or not. */ private function assertInfo($withTotals) { global $order; $order = new \order(); if ($withTotals) { if (!isset($shipping_modules)) { $shipping_modules = new \shipping($_SESSION['shipping']); } $order_total_modules = new \order_total(); $order_total_modules->collect_posts(); $order_total_modules->pre_confirmation_check(); $order_total_modules->process(); } foreach ($order->info as $key => $value) { if (in_array($key, array('rowClass', 'ip_address'))) { continue; } if (array_key_exists($key, $this->info)) { if ('tax_groups' == $key) { // drop [0] as that is the default for none in zc if (isset($value[0])) { unset($value[0]); } $mytg = $this->info[$key]; if (count($value) != count($mytg)) { echo 'info(' . ($withTotals ? 'with' : 'without') . ' ot): tax groups length diff! order: '; var_dump($value); echo 'ZM got: '; var_dump($mytg); echo '<br>'; } continue; } if (in_array($key, array('total', 'subtotal', 'tax'))) { $value = round($value, 3); $this->info[$key] = round($this->info[$key], 3); } if ((string) $value != (string) $this->info[$key]) { echo 'info(' . ($withTotals ? 'with' : 'without') . ' ot): value mismatch for ' . $key . ': value='; var_dump($value); echo ', ZM got: '; var_dump($this->info[$key]); echo "<BR>"; } } else { echo 'info(' . ($withTotals ? 'with' : 'without') . ' ot): missing key: ' . $key . ', value is: ' . $value . "<BR>"; } } echo '<br>'; }
function amazon_process_order($pAmazonOrderId) { global $gAmazonMWS, $gBitUser, $gCommerceSystem, $gBitCustomer, $currencies, $order; $ret = NULL; $request = new MarketplaceWebServiceOrders_Model_GetOrderRequest(); $request->setSellerId(MERCHANT_ID); // @TODO: set request. Action can be passed as MarketplaceWebServiceOrders_Model_GetOrderRequest // object or array of parameters // Set the list of AmazonOrderIds $orderIds = new MarketplaceWebServiceOrders_Model_OrderIdList(); $orderIds->setId(array($pAmazonOrderId)); $request->setAmazonOrderId($orderIds); $holdUser = $gBitUser; $azUser = new BitPermUser($holdUser->lookupHomepage($gCommerceSystem->getConfig('MODULE_PAYMENT_AMAZONMWS_LOCAL_USERNAME', 'amazonmws'))); $azUser->load(); $gBitUser = $azUser; $gBitCustomer = new CommerceCustomer($gBitUser->mUserId); $gBitCustomer->syncBitUser($gBitUser->mInfo); $_SESSION['customer_id'] = $gBitUser->mUserId; try { $response = $gAmazonMWS->getOrder($request); if ($response->isSetGetOrderResult()) { $getOrderResult = $response->getGetOrderResult(); if ($getOrderResult->isSetOrders()) { $oldCwd = getcwd(); chdir(BITCOMMERCE_PKG_PATH); $azOrderList = $getOrderResult->getOrders(); if ($azOrders = $azOrderList->getOrder()) { require_once BITCOMMERCE_PKG_PATH . 'classes/CommerceOrder.php'; $order = new order(); $order->info = array('order_status' => DEFAULT_ORDERS_STATUS_ID, 'subtotal' => 0, 'tax' => 0, 'total' => 0, 'tax_groups' => array(), 'comments' => isset($_SESSION['comments']) ? $_SESSION['comments'] : '', 'ip_address' => $_SERVER['REMOTE_ADDR']); $azOrder = current($azOrders); // Setup delivery address if ($orderTotal = $azOrder->getOrderTotal()) { $order->info['total'] = $orderTotal->getAmount(); $order->info['currency'] = $orderTotal->getCurrencyCode(); $order->info['currency_value'] = $currencies->currencies[$order->info['currency']]['currency_value']; } if ($shippingAddress = $azOrder->getShippingAddress()) { $country = zen_get_countries(zen_get_country_id($shippingAddress->getCountryCode()), TRUE); $zoneName = zen_get_zone_name_by_code($country['countries_id'], $shippingAddress->getStateOrRegion()); $order->delivery = array('firstname' => substr($shippingAddress->getName(), 0, strpos($shippingAddress->getName(), ' ')), 'lastname' => substr($shippingAddress->getName(), strpos($shippingAddress->getName(), ' ') + 1), 'company' => NULL, 'street_address' => $shippingAddress->getAddressLine1(), 'suburb' => trim($shippingAddress->getAddressLine2() . ' ' . $shippingAddress->getAddressLine3()), 'city' => $shippingAddress->getCity(), 'postcode' => $shippingAddress->getPostalCode(), 'state' => $zoneName, 'country' => $country, 'format_id' => $country['address_format_id'], 'telephone' => $shippingAddress->getPhone(), 'email_address' => NULL); $order->customer = $order->delivery; $order->billing = $order->delivery; } // Setup shipping $shipping = array('cost' => 0); switch ($azOrder->getShipServiceLevel()) { case 'Std US Dom': $shipping['id'] = 'usps_MEDIA'; $shipping['title'] = 'United States Postal Service (USPS Media Mail (1 - 2 Weeks))'; $shipping['code'] = 'USPSREG'; break; } $azOrderItems = amazon_mws_get_order_items($azOrder->getAmazonOrderId()); $azOrderItem = $azOrderItems->getOrderItem(); foreach ($azOrderItem as $azi) { $testSku = $azi->getSellerSKU(); list($productsId, $attrString) = explode(':', $testSku, 2); $productsKey = $productsId . ':ASIN-' . $azi->getASIN(); $order->contents[$productsKey] = $gBitCustomer->mCart->getProductHash($productsKey); $order->contents[$productsKey]['products_quantity'] = $azi->getQuantityOrdered(); $order->contents[$productsKey]['products_name'] = $azi->getTitle(); if ($itemPrice = $azi->getItemPrice()) { // {$itemTax->getCurrencyCode()} $order->contents[$productsKey]['price'] = $itemPrice->getAmount(); $order->contents[$productsKey]['final_price'] = $itemPrice->getAmount(); } if ($itemTax = $azi->getItemTax()) { // {$itemTax->getCurrencyCode()} $order->contents[$productsKey]['tax'] = $itemTax->getAmount(); } if ($shippingPrice = $azi->getShippingPrice()) { // {$itemTax->getCurrencyCode()} $order->info['shipping_cost'] = $shippingPrice->getAmount(); } if (empty($attrString)) { $attrString = $gCommerceSystem->getConfig('MODULE_PAYMENT_AMAZONMWS_DEFAULT_ATTRIBUTES'); } // stock up the attributes if ($attrString && ($attrs = explode(',', $attrString))) { foreach ($attrs as $optionValueId) { $optionId = $order->mDb->getOne("SELECT cpa.`products_options_id` FROM " . TABLE_PRODUCTS_ATTRIBUTES . " cpa WHERE cpa.`products_options_values_id`=?", array($optionValueId)); $order->contents[$productsKey]['attributes'][$optionId . '_' . $optionValueId] = $optionValueId; } } if (!empty($order->contents[$productsKey]['attributes'])) { $attributes = $order->contents[$productsKey]['attributes']; $order->contents[$productsKey]['attributes'] = array(); $subindex = 0; foreach ($attributes as $option => $value) { $optionValues = zen_get_option_value(zen_get_options_id($option), (int) $value); // Determine if attribute is a text attribute and change products array if it is. if ($value == PRODUCTS_OPTIONS_VALUES_TEXT_ID) { $attr_value = $order->contents[$productsKey]['attributes_values'][$option]; } else { $attr_value = $optionValues['products_options_values_name']; } $order->contents[$productsKey]['attributes'][$subindex] = array('option' => $optionValues['products_options_name'], 'value' => $attr_value, 'option_id' => $option, 'value_id' => $value, 'prefix' => $optionValues['price_prefix'], 'price' => $optionValues['options_values_price']); $subindex++; } } $shown_price = zen_add_tax($order->contents[$productsKey]['final_price'], $order->contents[$productsKey]['tax']) * $order->contents[$productsKey]['products_quantity'] + zen_add_tax($order->contents[$productsKey]['onetime_charges'], $order->contents[$productsKey]['tax']); $order->subtotal += $shown_price; $products_tax = $order->contents[$productsKey]['tax']; $products_tax_description = $order->contents[$productsKey]['tax_description']; if (DISPLAY_PRICE_WITH_TAX == 'true') { $order->info['tax'] += $shown_price - $shown_price / ($products_tax < 10 ? "1.0" . str_replace('.', '', $products_tax) : "1." . str_replace('.', '', $products_tax)); if (isset($order->info['tax_groups']["{$products_tax_description}"])) { $order->info['tax_groups']["{$products_tax_description}"] += $shown_price - $shown_price / ($products_tax < 10 ? "1.0" . str_replace('.', '', $products_tax) : "1." . str_replace('.', '', $products_tax)); } else { $order->info['tax_groups']["{$products_tax_description}"] = $shown_price - $shown_price / ($products_tax < 10 ? "1.0" . str_replace('.', '', $products_tax) : "1." . str_replace('.', '', $products_tax)); } } else { $order->info['tax'] += $products_tax / 100 * $shown_price; if (isset($order->info['tax_groups']["{$products_tax_description}"])) { $order->info['tax_groups']["{$products_tax_description}"] += $products_tax / 100 * $shown_price; } else { $order->info['tax_groups']["{$products_tax_description}"] = $products_tax / 100 * $shown_price; } } $order->info['tax'] = zen_round($order->info['tax'], 2); if ($azi->isSetShippingPrice()) { $shippingPrice = $azi->getShippingPrice(); $shipping['cost'] += $shippingPrice->getAmount(); } } foreach (array('cc_type', 'cc_owner', 'cc_number', 'cc_expires', 'coupon_code') as $key) { $order->info[$key] = NULL; } $order->info['shipping_method'] = $shipping['title']; $order->info['shipping_method_code'] = $shipping['code']; $order->info['shipping_module_code'] = $shipping['id']; $order->info['payment_module_code'] = 'amazonmws'; $order->info['payment_method'] = 'Amazon Order'; $_SESSION['sendto'] = NULL; $_SESSION['shipping'] = $shipping; unset($_SESSION['cot_gv']); require_once DIR_FS_CLASSES . 'order_total.php'; global $order_total_modules; $order_total_modules = new order_total(); $order_totals = $order_total_modules->pre_confirmation_check(); require_once DIR_WS_MODULES . 'payment/amazonmws.php'; $amazon = new amazonmws($azOrder->getAmazonOrderId()); $amazonOutput = $amazon->process(); $order_totals = $order_total_modules->process(); array_splice($order_totals, count($order_totals) - 1, 0, array($amazonOutput)); if ($ordersId = $order->create($order_totals, 2)) { $order->create_add_products($ordersId); $ret = $ordersId; $order->updateStatus(array('status' => MODULE_PAYMENT_AMAZONMWS_INITIAL_ORDER_STATUS_ID)); } } chdir($oldCwd); } } } catch (MarketplaceWebServiceOrders_Exception $ex) { echo "Caught Exception: " . $ex->getMessage() . "\n"; echo "Response Status Code: " . $ex->getStatusCode() . "\n"; echo "Error Code: " . $ex->getErrorCode() . "\n"; echo "Error Type: " . $ex->getErrorType() . "\n"; echo "Request ID: " . $ex->getRequestId() . "\n"; echo "XML: " . $ex->getXML() . "\n"; } $gBitUser = $holdUser; $gBitCustomer = new CommerceCustomer($gBitUser->mUserId); $_SESSION['customer_id'] = $gBitUser->mUserId; return $ret; }