·您现在的位置: 云翼网络 >> 文章中心 >> 网站建设 >> 网站建设开发 >> php网站开发 >> Zencart先生成订单后付款,类似淘宝后台修改订单价格

Zencart先生成订单后付款,类似淘宝后台修改订单价格

作者:佚名      php网站开发编辑:admin      更新时间:2022-07-23
Zencart先生成订单后付款,类似淘宝后台修改订单价格

Zencart 使用 Paypal 付款,会出现漏单的情况,即 paypal 已经收到客户的付款,但是网站后台没有客户的订单。导致 paypal 漏单的原因大致会是当客户跳转到Paypal 网站付款完毕之后,直接关闭了窗口,或者网络不稳定,没有正常跳转到网站。

解决 Paypal 漏单问题的方案有好几种:

一. 开启 Detailed Line Items in Cart 选项。

原理:在 zencart 后台 Module --> Payment --> PayPal Website Payments Standard - ipN 开启 Detailed Line Items in Cart 选项。这个选项会把你所有的订单物品信息传给 paypal,当客户付款成功而后台未能成功生成订单时,也可以通过 paypal 帐号交易信息看到客户购买了哪些物品。

二. 使用 Paypal sessions Viewer 插件找回 Paypal 漏掉的订单。

原理:zencart 购物车的物品,通过 paypal 方式付款,会在 paypal_session 表中保存此次付款的所有记录,如果付款成功后,从 paypal 网站跳转到购物网站并生成了订单时,zencart系统会自动删除这条 paypal_session 记录,如果没有成功跳转到购物网站,没有成功生成订单,那这条付款记录数据就会一直保存在数据库,当使用 Paypal Session Viewer 插件,就能查看这条记录的所有数据,包括客户信息,购物时间,商品信息,如果你确定已收到款,就可以把这条 paypal_session 信息转移到订单中,生成一个订单。

插件下载地址:http://www.zen-cart.cn/english-version-modules/admin-tools/paypal-sessions-viewer

三. 修改付款流程,先生成订单后付款。

原理:用过zen-cart的人都知道,zen-cart中下单步骤是下面这样的(其中[]中的表示不是必须的):

1. 购物车(shopping cart)

2. [货运方式(delivery method)]

3. 支付方式(payment method)

4. 订单确认(confirmation)

5. [第三方网站支付]

6. 订单处理(checkout PRocess)——这一步比较重要,因为会在这里将购物车中的信息写入订单

7. 下单成功(checkout success)

这样的流程在正常情况下是没有任何问题的。但是,从第5步到第6部的过程中,用户可能以为付款成功就直接关闭掉网页了,或者由于网络原因造成不能正常跳转到checkout_process页面,这样造成的后果是很严重的,因为订单不能被正常的创建。基于上述的分析, 我们希望稍微地改变一下流程,即在支付之前订单已经创建好了,这样就算在支付时不能从第三方支付网站跳转回来,我们也不会存在用户付款成功却在后台没有订单的情况了。

本人是参照东国先生的这篇修改zen-cart下单和付款流程以防止漏单 教程去修改的,因为这个教程比较老,而且也没有很全面,所以我根据自己的实际需求,把他做的更完善,更细节化。

经过修改后的蓝图基本是下面这样的:

1. 在checkour_confirmation页面确认订单后,都会直接proccess,并且进入 account_history_info 页面,可以在这里进入付款页面。如下图所示:

2. 如果当时客户没能付款,也可进入自己的后台对历史订单进行付款。如下图所示:

3. 未付款的订单,可以在后台修改价格,像淘宝一样拍下宝贝后,店主给你修改价格后再付款一样。如下图所示:

下面我们来正式修改代码,首先我列举出所有要修改的文件:

1. includes/classes/payment.php

2. includes/modules/payment/paypal.php

3. includes/classes/order.php

4. includes/modules/pages/checkout_process/header_php.php

5. includes/modules/pages/account_history_info/header_php.php

6. includes/templates/你的模板目录/templates/tpl_account_history_info_default.php

7. includes/templates/你的模板目录/templates/tpl_account_history_default.php

8. ipn_main_handler.php

9. admin(后台目录)/orders.php

因为先生成订单再付款,付款步骤就会比原来又多了一步,为了简化付款流程,我安装了 Fast And Easy Checkout For Zencart(快速支付) 插件,安装此插件之前,需要安装另外一个插件 CSS Js Loader For Zencart,这是快速支付插件的依赖插件。快速支付与先生成订单后支付没什么因果关系,所以如果你不想安装的话完全可以不理。

按步骤修改上面列举的文件:

1. 首先我们需要对现有的支付模块进行一个改造。需要对支付方式的class增加一个字段paynow_action_url,用来表示进行支付的页面 url,另外还需要增加一个函数,paynow_button($order_id),来获取支付表单的参数隐藏域代码。

要增加 paynow_action_url 变量,请在类payment的构造函数中最后加上下面的代码:

if ( (zen_not_null($module)) && (in_array($module.'.php', $this->modules)) && (isset($GLOBALS[$module]->paynow_action_url)) ) {        $this->paynow_action_url = $GLOBALS[$module]->paynow_action_url;        }

要增加paynow_button($order_id)函数,请在payment类的最后一个函数之后加上如下的代码:

function paynow_button($order_id){    if (is_array($this->modules)) {      if (is_object($GLOBALS[$this->selected_module])) {        return $GLOBALS[$this->selected_module]->paynow_button($order_id);      }    }}

2. 以paypal支付方式为例子,说明如何具体实现。这里直接修改 paypal.php 文件,注意备份此文件。代码如下所示,可以看到,这里去掉了对 form_action_url 的指定,并给定了 paynow_action_url,因为我们希望用户点击“确认订单”后直接进入checkout_process,所以如果不指定 form_action_url,那么确认订单的表单就会直接提交到 checkout_process 页面了,而 paynow_action_url 就是 以前的 form_action_url 的值。paynow_button 函数的实现也很简单,这里只是将原先的 process_button() 函数的内容剪切过来而已,只不过我们没有使用全局的$order变量,而是使用 $order = new order($order_id),来重新构造的一个对象,这样做是为在历史订单中显示pay now按钮做准备的。paypal.php修改后的文件如下:

  1 <?php  2 /**  3  * paypal.php payment module class for PayPal Website Payments Standard (IPN) method  4  *  5  * @package paymentMethod  6  * @copyright Copyright 2003-2010 Zen Cart Development Team  7  * @copyright Portions Copyright 2003 osCommerce  8  * @license http://www.zen-cart.com/license/2_0.txt GNU Public License V2.0  9  * @version $Id: paypal.php 15735 2010-03-29 07:13:53Z drbyte $ 10  */ 11  12 define('MODULE_PAYMENT_PAYPAL_TAX_OVERRIDE', 'true'); 13  14 /** 15  *  ensure dependencies are loaded 16  */ 17   include_once((IS_ADMIN_FLAG === true ? DIR_FS_CATALOG_MODULES : DIR_WS_MODULES) . 'payment/paypal/paypal_functions.php'); 18  19 /** 20  * paypal.php payment module class for PayPal Website Payments Standard (IPN) method 21  * 22  */ 23 class paypal extends base { 24   /** 25    * string representing the payment method 26    * 27    * @var string 28    */ 29   var $code; 30   /** 31    * $title is the displayed name for this payment method 32    * 33    * @var string 34     */ 35   var $title; 36   /** 37    * $description is a soft name for this payment method 38    * 39    * @var string 40     */ 41   var $description; 42   /** 43    * $enabled determines whether this module shows or not... in catalog. 44    * 45    * @var boolean 46     */ 47   var $enabled; 48   /** 49     * constructor 50     * 51     * @param int $paypal_ipn_id 52     * @return paypal 53     */ 54   function paypal($paypal_ipn_id = '') { 55     global $order, $messageStack; 56     $this->code = 'paypal'; 57     $this->codeVersion = '1.3.9'; 58     if (IS_ADMIN_FLAG === true) { 59       $this->title = MODULE_PAYMENT_PAYPAL_TEXT_ADMIN_TITLE; // Payment Module title in Admin 60       if (IS_ADMIN_FLAG === true && defined('MODULE_PAYMENT_PAYPAL_IPN_DEBUG') && MODULE_PAYMENT_PAYPAL_IPN_DEBUG != 'Off') $this->title .= '<span class="alert"> (debug mode active)</span>'; 61       if (IS_ADMIN_FLAG === true && MODULE_PAYMENT_PAYPAL_TESTING == 'Test') $this->title .= '<span class="alert"> (dev/test mode active)</span>'; 62     } else { 63       $this->title = MODULE_PAYMENT_PAYPAL_TEXT_CATALOG_TITLE; // Payment Module title in Catalog 64     } 65     $this->description = MODULE_PAYMENT_PAYPAL_TEXT_DESCRIPTION; 66     $this->sort_order = MODULE_PAYMENT_PAYPAL_SORT_ORDER; 67     $this->enabled = ((MODULE_PAYMENT_PAYPAL_STATUS == 'True') ? true : false); 68     if ((int)MODULE_PAYMENT_PAYPAL_ORDER_STATUS_ID > 0) { 69       $this->order_status = MODULE_PAYMENT_PAYPAL_ORDER_STATUS_ID; 70     } 71     if (is_object($order)) $this->update_status(); 72     $this->paynow_action_url = 'https://' . MODULE_PAYMENT_PAYPAL_HANDLER; 73  74     if (PROJECT_VERSION_MAJOR != '1' && substr(PROJECT_VERSION_MINOR, 0, 3) != '3.9') $this->enabled = false; 75  76     // verify table structure 77     if (IS_ADMIN_FLAG === true) $this->tableCheckup(); 78   } 79   /** 80    * calculate zone matches and flag settings to determine whether this module should display to customers or not 81     * 82     */ 83   function update_status() { 84     global $order, $db; 85  86     if ( ($this->enabled == true) && ((int)MODULE_PAYMENT_PAYPAL_ZONE > 0) ) { 87       $check_flag = false; 88       $check_query = $db->Execute("select zone_id from " . TABLE_ZONES_TO_GEO_ZONES . " where geo_zone_id = '" . MODULE_PAYMENT_PAYPAL_ZO