微擎开发之人人商城添加第三方支付系列

背景介绍

商城采用的是基于微擎开发的人人商城,做的是跨境电商,需要接入通联支付打通跟环球云仓和海关那边报关的需要,首先要接入通联支付进入系统中。申请好需要的基础信息包括商户号、appid等。文档地址:https://aipboss.allinpay.com/know/devhelp/index.php

接入通联支付之H5收银宝支付

在core/model目录下新建一个文件,比如说叫tlpay.php,直接上代码

<?php

if (!defined('IN_IA')) {
    exit('Access Denied');
}
class Tlpay_EweiShopV2Model{
    /**
     * 支付商户号
     * @var string
     */
    public static $CUSID;
    /**
     * 支付appid
     * @var string
     */
    public static $APPID;
    /**
     * md5加密key
     * @var string
     */
    public static $KEY;
    /**
     *字符集
     * @var string
     */
    public static $CHARSET ='';
    /**
     * 版本
     * @var string
     */
    public static $VERSION;
    /**
     * 支付请求地址
     * @var string
     */
    public static $URL;

    /**
     * 获取签名
     * @param $array
     * @param $appkey
     * @return string
     */
    public function SignArray($array,$appkey){
        $array['key'] = $appkey;// 将key放到数组中一起进行排序和组装
        ksort($array);
        $blankStr = $this->ToUrlParams($array);
        $sign = strtoupper(md5($blankStr));
        return $sign;
    }

    /**
     * @param $array
     * @return string
     */
    public function ToUrlParams($array)
    {
        $buff = "";
        foreach ($array as $k => $v)
        {
            if($v != "" && !is_array($v)){
                $buff .= $k . "=" . $v . "&";
            }
        }

        $buff = trim($buff, "&");
        return $buff;
    }

    /**
     * @param array $array
     * @param $appkey
     * @return bool
     */
    public function ValidSign(array $array,$appkey){
        $sign = $array['sign'];
        unset($array['sign']);
        $array['key'] = $appkey;
        $mySign = $this->SignArray($array, $appkey);
        return strtolower($sign) == strtolower($mySign);
    }

    /**
     * 组织数据
     * @param $order_id
     * @return array|bool
     */
    public function postData($order_id)
    {
        if($order_id==''){
            return false;
        }
        $redirect_url = mobileUrl('order/pay/success',array('id'=>$orderid,'result'=>"true")); //支付成功后跳转地址
        $redirect_url ='http://'.$_SERVER['HTTP_HOST'].'/app/'.substr($redirect_url,2);
        $orderInfo  = pdo_get('ewei_shop_order',['id'=>$order_id],['ordersn','price']);
        $params = array();
        $params["cusid"] = static::$CUSID;
        $params["appid"] = static::$APPID;
        $params["version"] = static::$VERSION;
        $params["orgid"] = '';
        $params["randomstr"] =$this->createNoncestr();
        $params["trxamt"] = $orderInfo['price']*100;//订单金额
        $params["reqsn"] = $orderInfo['ordersn'];//订单号
        $params["charset"] = static::$CHARSET;//mobileUrl("order/pay/success", array( "id" => $order["id"], "type" => "credit", "ordersn" => $order["ordersn"] ))
        //$params["returl"] = 'http://'.$_SERVER['HTTP_HOST'].'/app/'.substr(mobileUrl('order/pay/complete',array('id'=>$orderid,"type" => "tlpay")),2);//self::$data['returl'];
        $params["returl"] = $redirect_url;//mobileUrl("order/pay/success", array( "id" => $order_id, 'result'=>"true","type" => "tlpay"));
        $params["notify_url"] ='http://'.$_SERVER['HTTP_HOST']."/addons/ewei_shopv2/payment/tlpay/notify.php";
        $params["body"] = 'xxxx';
        $params["remark"] = 'xxxx';
        $params["validtime"] = '10';
        $params["limit_pay"] ='no_credit';
        $params["asinfo"] ='';
        $sign = $this->SignArray($params,static::$KEY);
        $params['sign'] = $sign;
        return $params;

    }

    /**
     * 模拟微信浏览器 参考网上的代码
     * @param $url
     * @param $data
     * @param $referer
     * @param $cookie
     * @return mixed
     */
    public function makeHttp($url, $data, $referer, $cookie)
    {
        $header = array();
        $header[] = 'Accept: image/gif, image/jpeg, image/pjpeg, image/pjpeg, application/x-ms-application, application/x-ms-xbap, application/vnd.ms-xpsdocument, application/xaml+xml, */*';
        $header[] = 'Connection: Keep-Alive';
        $header[] = 'Accept-Language: zh-cn';
        $header[] = 'Cache-Control: no-cache';
        $ch = curl_init();
        curl_setopt($ch, CURLOPT_URL, $url);
        curl_setopt($ch, CURLOPT_POST, 1);
        //curl_setopt($ch, CURLOPT_HEADER, 1);
        curl_setopt($ch, CURLOPT_HTTPHEADER, $header);
        curl_setopt($ch, CURLOPT_USERAGENT, 'Mozilla/5.0 (Linux; U; Android 2.3.6; zh-cn; GT-S5660 Build/GINGERBREAD) AppleWebKit/533.1 (KHTML, like Gecko) Version/4.0 Mobile Safari/533.1 MicroMessenger/4.5.255');
        curl_setopt($ch, CURLOPT_REFERER, $referer);
        curl_setopt($ch, CURLOPT_COOKIE, $cookie);
        curl_setopt($ch, CURLOPT_POSTFIELDS, http_build_query($data));
        curl_setopt($ch, CURLOPT_RETURNTRANSFER, 1);
        curl_setopt($ch, CURLOPT_TIMEOUT, 10);
        $result = curl_exec($ch);
        curl_close($ch);
        return $result;

    }

    /**
     *  作用:产生随机字符串,不长于32位
     */
    public function createNoncestr( $length = 32 ){
        $chars = "abcdefghijklmnopqrstuvwxyz0123456789";
        $str ="";
        for ( $i = 0; $i < $length; $i++ )  {
            $str.= substr($chars, mt_rand(0, strlen($chars)-1), 1);
        }
        return $str;
    }

}

在pay.php的success方法中加入针对通联支付的处理

接入通联支付之商户支付验证报关接口

代码如下:

<?php

namespace app\xxxxxx\library;

use think\Db;

class Tlpay
{
    private static $data = array(
        'VERSION' => 'v5.6',//版本
        'VISITOR_ID' => 'MCT',//接入方ID
        'MCHT_ID' => 'xxxx',//报关用的商户号
        'CHARSET' => '1',//字符集
        'SIGN_TYPE' => '1',//签名方式
        'CUSTOMS_CODE' => 'xxxxxx',//海关类别
        'PAYMENT_CHANNEL' => '2',//支付渠道
        'CUS_ID' => 'xxxxxxxx',//支付用的商户号
        'CURRENCY' => '156',//支付币制
        'ESHOP_ENT_CODE' => 'xxxxxxx',//电商平台代码
        'ESHOP_ENT_NAME' => 'xxxxxxxx',//电商平台名称
        'PAPER_TYPE' => '01',//支付人证件类型
        'PRO_URL' => 'https://service.allinpay.com/customs/pvcapply',//生产环境
        'DEV_URL' => '',//测试环境
    );

    /**
     * 格式化数据
     * @param $data
     * @param DOMDocument|null $dom
     * @param DOMElement|null $xml
     * @param string $ele
     * @return mixed
     */
    public static function convert($data, \DOMDocument $dom = null, \DOMElement $xml = null, $ele = 'PAYMENT_INFO')
    {
        if (!$dom) {
            $dom = new \DOMDocument('1.0', 'UTF-8');
            $dom->formatOutput = true;
        }
        if (!$xml) {
            $xml = $dom->createElement($ele);
            $dom->appendChild($xml);
        }
        foreach ($data As $key => $val) {
            $key = !is_string($key) ? $xml->tagName : $key;
            if (is_array($val) && count($val) && preg_match('/^[\d]+$/', implode('', array_keys($val)))) {
                foreach ($val As $k => $v) {
                    $e = $dom->createElement($key);
                    $xml->appendChild($e);

                    if (is_object($v) || is_array($v)) {
                        self::convert($v, $dom, $e);
                        continue;
                    }
                    if (is_string($v) && preg_match('/<[^>]+>/', $v)) {
                        $e->appendChild($dom->createCDATASection($v));
                    } else {
                        $e->nodeValue = htmlspecialchars((string)$v);
                    }
                }
                continue;
            }
            if ((is_object($val) || is_array($val)) && count($val)) {
                $e = $dom->createElement($key);
                $xml->appendChild($e);
                self::convert($val, $dom, $e);
                continue;
            }
            if ((is_object($val) || is_array($val)) && !count($val)) {
                $xml->appendChild($dom->createElement($key));
                continue;
            }
            $e = $dom->createElement($key);
            $xml->appendChild($e);
            if (is_string($val) && preg_match('/<[^>]+>/', $val)) {
                $e->appendChild($dom->createCDATASection($val));
            } else {
                $e->nodeValue = htmlspecialchars((string)$val);
            }
        }
        return $dom->saveXML();
    }

    /**
     * 获取签名
     * @param $str
     * @return string
     */
    public function get_sign($str)
    {
        $sdata = substr($str, 39);
        $par = array(" ", " ", "\t", "\n", "\r");
        $re = str_replace($par, '', $sdata);
        $md5key = 'xxxxxxxxxxx';
        $mstr = $re . '<key>' . $md5key . '</key>';
        $md5re = strtoupper(md5($mstr));
        return $md5re;
    }

    /**
     * 截取标准xml数据组合紧密数据
     * @param $str
     * @return mixed
     */
    public function cut_str($str)
    {
        $sdata = substr($str, 39);
        $par = array(" ", " ", "\t", "\n", "\r");
        $re = str_replace($par, '', $sdata);
        return $re;
    }

    /**
     * cURL http请求
     * @param $url
     * @param $params
     * @param string $method
     * @return mixed
     */
    private function http($url, $params = array(), $method = "POST", $headers = array())
    {
        $ch = curl_init();
        curl_setopt($ch, CURLOPT_URL, $url);
        curl_setopt($ch, CURLOPT_RETURNTRANSFER, TRUE);
        curl_setopt($ch, CURLOPT_CUSTOMREQUEST, $method);
        curl_setopt($ch, CURLOPT_SSL_VERIFYPEER, false); // 对认证证书来源的检查
        curl_setopt($ch, CURLOPT_SSL_VERIFYHOST, false); // 从证书中检查SSL加密算法是否存在
        curl_setopt($ch, CURLOPT_POST, TRUE);
        curl_setopt($ch, CURLOPT_HEADER, FALSE);
        curl_setopt($ch, CURLOPT_POSTFIELDS, $params);
        curl_setopt($ch, CURLOPT_HTTPHEADER, $headers);
        if ($headers != "") {
            curl_setopt($ch, CURLOPT_HTTPHEADER, $headers);
        } else {
            curl_setopt($ch, CURLOPT_HTTPHEADER, array('Content-type: application/x-www-form-urlencoded'));
        }

        $output = curl_exec($ch);
        curl_close($ch);
        return $output;//base64格式的
    }

    /**
     * xml转数组
     * @param $xml
     * @return mixed
     */
    public function xml_array($xml)
    {
        //禁止引用外部xml实体
        libxml_disable_entity_loader(true);
        $values = json_decode(json_encode(simplexml_load_string($xml, 'SimpleXMLElement', LIBXML_NOCDATA)), true);
        return $values;

    }

    /**
     * 获取响应信息解码 base64转码 然后转数组
     * @param $str
     * @return mixed
     */
    public function decode_res($str)
    {
        $res = base64_decode($str);
        $header_str = '<?xml version="1.0" encoding="UTF-8"?>';
        $new_str = $header_str . $res;
        $result = $this->xml_array($new_str);
        return $result;

    }

    /**
     * 根据订单获取信息
     * @param $ordersn
     */
    public function get_orderinfo($ordersn)
    {
        $info = Db::table('ims_ewei_shop_order')
            ->alias('a')
            ->join('ims_ewei_shop_member_address b', 'a.addressid = b.id ', 'LEFT')
            ->field('a.price,a.paytime,a.transid,b.realname,b.mobile,b.purchaser_id')
            ->where('a.paytype', '=', xx)
            ->where('b.realname IS NOT NULL')
            ->where('b.mobile IS NOT NULL')
            ->where('b.purchaser_id IS NOT NULL')
            ->where('a.ordersn', '=', $ordersn)
            ->find();
        return $info;
    }

    /**
     * @param $ordersn
     * @return array
     */
    public function get_body($ordersn)
    {
        $info = $this->get_orderinfo($ordersn);

        $bodyData = array(
            'CUSTOMS_CODE' => self::$data['CUSTOMS_CODE'],
            'PAYMENT_CHANNEL' => self::$data['PAYMENT_CHANNEL'],//支付渠道
            'CUS_ID' => self::$data['CUS_ID'],//支付用的商户号
            'PAYMENT_DATETIME' => date("YmdHis", $info['paytime']),
            'MCHT_ORDER_NO' => $ordersn,
            'PAYMENT_ORDER_NO' => $info['transid'],
            'PAYMENT_AMOUNT' => $info['price'] * 100,//支付总额 分
            'CURRENCY' => self::$data['CURRENCY'],//支付币制
            'ESHOP_ENT_CODE' => self::$data['ESHOP_ENT_CODE'],//电商平台代码
            'ESHOP_ENT_NAME' => self::$data['ESHOP_ENT_NAME'],//电商平台名称
            'PAYER_NAME' => $info['realname'],//支付人姓名
            'PAPER_TYPE' => self::$data['PAPER_TYPE'],//支付人证件类型
            'PAPER_NUMBER' => $info['purchaser_id'],//支付人证件号码
            'PAPER_PHONE' => $info['mobile'],//支付人手机号
            'PAPER_EMAIL' => '',//支付人邮箱

        );
        $xmlData = self::convert($bodyData, null, null, $ele = 'BODY');
        return $xmlData;
    }

    /**
     * 组合数据
     * @param $ordersn
     */
    public function format_data($ordersn)
    {
        $bodyXml = $this->get_body($ordersn);
        $info = $this->get_orderinfo($ordersn);
        $params = array();
        $params['HEAD']['VERSION'] = self::$data['VERSION'];
        $params['HEAD']['VISITOR_ID'] = self::$data['VISITOR_ID'];
        $params['HEAD']['MCHT_ID'] = self::$data['MCHT_ID'];
        $params['HEAD']['ORDER_NO'] = $ordersn;
        $params['HEAD']['TRANS_DATETIME'] = date('YmdHis');
        $params['HEAD']['CHARSET'] = self::$data['CHARSET'];
        $params['HEAD']['SIGN_TYPE'] = self::$data['SIGN_TYPE'];
        $params['HEAD']['SIGN_MSG'] = $this->get_sign($bodyXml);
        $params['BODY']['CUSTOMS_CODE'] = self::$data['CUSTOMS_CODE'];
        $params['BODY']['PAYMENT_CHANNEL'] = self::$data['PAYMENT_CHANNEL'];
        $params['BODY']['CUS_ID'] = self::$data['CUS_ID'];
        $params['BODY']['PAYMENT_DATETIME'] = date("YmdHis", $info['paytime']);
        $params['BODY']['MCHT_ORDER_NO'] = $ordersn;
        $params['BODY']['PAYMENT_ORDER_NO'] = $info['transid'];
        $params['BODY']['PAYMENT_AMOUNT'] = $info['price'] * 100;
        $params['BODY']['CURRENCY'] = self::$data['CURRENCY'];
        $params['BODY']['ESHOP_ENT_CODE'] = self::$data['ESHOP_ENT_CODE'];
        $params['BODY']['ESHOP_ENT_NAME'] = self::$data['ESHOP_ENT_NAME'];
        $params['BODY']['PAYER_NAME'] = $info['realname'];
        $params['BODY']['PAPER_TYPE'] = self::$data['PAPER_TYPE'];
        $params['BODY']['PAPER_NUMBER'] = $info['purchaser_id'];
        $params['BODY']['PAPER_PHONE'] = $info['mobile'];
        $params['BODY']['PAPER_EMAIL'] = '';
        $xmlInfo = self::convert($params);
        $mainInfo = $this->cut_str($xmlInfo);
        return base64_encode($mainInfo);
    }

    /**获取结果
     * @param $ordersn
     */
    public function get_res($ordersn)
    {
        $post = $this->format_data($ordersn);
        $data = "data=" . urlencode($post);
        $url = self::$data['PRO_URL'];
        $res = $this->http($url, $data);
        $data = $this->decode_res($res);
        //dump($data);
        $log['ordersn'] = $data['HEAD']['ORDER_NO'];
        $log['ctime'] = time();
        $log['utime'] = time();
        if ($data['BODY']['RETURN_CODE'] == '0000') {
            $log['status'] = 1;
        } else {
            $log['status'] = 2;
            $log['errmsg'] = $data['BODY']['RETURN_MSG'];
        }
        Db::name('xxxxxxxx')->insert($log);
        Db::name('ewei_shop_order')->where('ordersn', $data['HEAD']['ORDER_NO'])->update(['tl_sync_status' => $log['status']]);
        return true;
    }
}

原文地址:https://www.cnblogs.com/weblm/p/11013268.html

时间: 2024-11-09 03:10:27

微擎开发之人人商城添加第三方支付系列的相关文章

人人商城添加虚拟商品支持线下核销的方法

1.修改以下文件:addons/ewei_shopv2/template/web_v3/goods <li {if $_GPC['tab']=='verify'}class="active"{/if} id="tab_nav_verify" {if $item['type']==3||$item['type']==5||($item['type']==2&&!empty($item['virtualsend']))}style="di

微擎/微赞开发示例 学习记录

//微擎 开发一个便利店 步骤一. 需求分析 首先,你要明确你做的模块包含什么功能. 便利店管理 — (store) 商品管理 — (goods) 客户管理 — (customers) 订单管理 — (orders) 购物车与支付 — (cart) 统计功能 — (statistics) (待续…) 步骤二. 设计新模块 开始设计新模块前,你要知道通过你的模块用户能干什么, 并起一个很棒的英文名字. 操作用户能干什么   微信用户能干什么 1. 管理便利店 (store) 1. 逛便利店 (st

关于微擎小程序的操作的步骤,如何上传小程序?

2018年,微信小程序,到了风口期了,小龙欧巴,孵化了快1年多的项目,注定会成为大家经常接触的项目, 微擎,基于微信第三方的开发框架,的确好用,只是文档的更新貌似永久性停留在了2017年4月份啦! https://www.we7.cc/manual/index.php 故鄙人特开此博客,来记录学习微擎开发过程中的各种神坑. 第一讲:讲解如何安装微擎小程序 (1).配置环境 微擎是基于php的开发框架,故要搭载好php的运行环境: 可以自己分个下载php.mysql.apache进行配置安装: 或

微擎app端上传图片后删除不了图片

相信在微擎开发的哥们都知道, 微擎在手册方面还是有点坑的,根本不让人活啊.没办法, 开发时, 只能自己看着源码来搞>>>> 好, 不多说了. 现在来看一个坑  ..直接上代码\ html: <!--自己的头部引入-->{template 'common_header'} <script type="text/javascript" src="{$_W['siteroot']}app/resource/js/app/util.js&qu

第三方支付平台的安全策略

在清算的情况下,这导致支付平台账户上剩余大量资金,从而形成资金.融资融券软件开发这些资金可以在第三方支付平台上停留3天到一周,有些可以停留几年.如果第三方支付平台恶意挪用资金或者将资金用于风险投资,一旦出现问题将严重影响公众对第三方支付平台的信任.电子商务交易甚至整个社会都将面临巨大的风险,这将引发社会信用危机.目前,只有支付宝将这些资金存入银行的专有账户,其他支付平台的资金面临此类安全风险. 多种技术手段确保用户安全 在第三方在线支付过程中,很难避免技术风险,而支付各方面的技术问题将直接或间接

微擎人人商城二次开发01

刚开始工作就接触微擎人人商城的二次开发,折腾了很久下面总结下我所学到的: 首先是安装包ewei_shopv2: 将后端ewei_shopv2文件夹上传至微赞微擎Addons目录 文件夹介绍 路由:http://*******/web/index.php?c=site&a=entry&m=ewei_shopv2&do=web&r=agency.productc = site :a = entry表示后台模块m 表示具体哪个模块do 要执行的site类中的doWeb***方法r

登录微擎后台直接跳转到人人商城后台首页

登录微擎后台直接跳转到人人商城后台首页 置顶 2018年05月28日 10:01:09 若谷工作室 阅读数:2471更多 个人分类: php人人商城  小程序人人商城二开 路径:web/source/user/login.ctrl.php if ($record['username']=='admin') { isetcookie('__uniacid', 1, 7 * 86400); header('location:'.url('site/entry/web',array('m'=>'ewe

微擎模块人人商城替换版本方法

原网址:http://www.souho.net/thread-1073253-1-2.html 如果你微赞网站的数据库里之前安装过或者正在使用别的版本的人人商城,即便是卸载再安装新版人人商城模块可能也会导致安装后无法找新版里新增的一些应用(如安装后不显示"区域代理"应用等),如遇到此问题请按照以下方法操作(没有遇到的话下面操作不用理会): 1,在微赞网站后台模块管理那里卸载人人商城模块,然后删除addons目录下的ewei_shopv2文件夹 2,删除你微赞数据库里所有以 ims_e

第二篇 基于微擎的模块开发—PHP

从陌生到如今能勉强完成第一个微网站模块的实现.也算是一个小小的进步,从设计数据库到,返回数据,前端模版渲染 每一点都是有点难度的.所以我想总结一下,我是如何实现一个微擎模块. 第一,首先得分析某个模块的想实现什么需求,根据需求设计合理的数据库结构. 第二,了解微擎的结构,运行流程,设计模块结构. 第三,重点就是site.php , 完成site.php 需要一定的php的编程能力, 第四,site.php 其中 通过 pdo 从数据库的获取我们想得到数据源. 微擎已封装其路由机制, doWeb