thinkphp集成palpay支付

很久很久以前做过paypal的支付,最近在github上paypal的sdk,感觉变成庞然大物了。
于是索性看看以前的理理看看以前的代码,适当修改一下就用起来了,新的sdk太费时了。
paypal的支付流程基本如下
1.发起支付
2.用户进入付款,paypal异步向网站预设定接口发送通知
3.接口收到用户付款相关状态的通知后,再次向paypal进入消息的核实
4.消息核实通过后,更新订单状态
5.用户支付完成,并跳转回网站
这其中2、3、4都是异步进行的,业务层面还有一些待完善的地方,比如token更严格,比如防止重复支付等。

以下是paypal sandbox url,正式使用时换成正式url

<?php
namespace Home\Controller;
use Think\Controller;   
class PaypalController extends Controller {
    protected $gateway;
    protected $business;
    protected $return;
    protected $notify_url;
    protected $ipnurl;

    public function _initialize() {
        //$this->gateway = 'https://www.paypal.com/us/cgi-bin/webscr';
        $this->ipnurl = 'https://ipnpb.sandbox.paypal.com/cgi-bin/webscr?';
        $this->gateway = 'https://www.sandbox.paypal.com/us/cgi-bin/webscr';
        $this->notify_url = 'http://demo.xxxx.com/home/paypal/notify';
        $this->business = 'xxxxx@yeah.net';
        $this->return = 'http://demo.xxxx.com/home/paypal/success';
    }

    public function pay()
    {
        if (!isset($_SESSION["user_login_id"])) {
            $this->redirect("/user/login");
        }

        if (isset($_GET['order_number']) && isset($_GET['price']) && isset($_GET['token'])) {

            //验证token
            if ($_GET['token'] != md5($_GET['order_number'] . $_GET['price'] . 'aRgs#&gpd')) {
                echo 'token error!';
                die();
            }

            $this->assign('price', $_GET['price']);
            $this->assign('order_number', $_GET['order_number']);
        }

        if (isset($_GET['order_number'])) {

            $user = M("userinfo")->where(array('id'=>$_SESSION["user_login_id"]))->find();
            $this->assign('user', $user);
            $product_name = $user['name'] . ' \'s shipping order';
            $this->assign('product_name', $product_name);
            $this->assign('gateway', $this->gateway);
            $this->assign('business', $this->business);
            $this->assign('return', $this->return);
            $this->assign('notify_url', $this->notify_url);
            $this->display();
        }else{
            die('unkown error');
        }

    }

    public function paypal_log($msg='test',$file=''){
        if($file=='')$file='paypal_vg_x_'.date('Ymd',time()).'.log';
        file_put_contents($_SERVER['DOCUMENT_ROOT'].'/'.$file,$msg.PHP_EOL,FILE_APPEND);
    }


    public function notify(){
        //从 PayPal 出读取 POST 信息同时添加变量"cmd‟ 进行二次核验使用
        $req = 'cmd=_notify-validate';
        foreach ($_POST as $key => $value) {
            $value = urlencode(stripslashes($value));
            $req .= "&$key=$value";
        }
        $item_name = $_POST['item_name'];
        $item_number = $_POST['item_number'];
        $payment_status = $_POST['payment_status'];
        $payment_amount = $_POST['mc_gross'];  //支付的金额
        $payment_currency = $_POST['mc_currency']; //币种
        $txn_id = $_POST['txn_id'];
        $receiver_email = $_POST['receiver_email'];
        $payer_email = $_POST['payer_email'];
        $orderNumber=$item_number;
        //记录paypal返回的日志
        $this->paypal_log($req);

        //---------------------------------------
        /**向paypal求证以上信息是否自己paypal**/
        $order = M('order')->where(array('order_id'=>$orderNumber))->find();//
        if(empty($order)){
            $this->paypal_log('订单不存在');
            die();
        }
        $this->paypal_log('订单信息:'.json_encode($order));
        //金额检查
        if($order['amount'] != $payment_amount){
            $this->paypal_log('金额不对,原订单为'.$order['amount'].'支付金额为'.$payment_amount);
            die();
        }else{
            $url=$this->gateway.'?'.$req;
            $ch = curl_init();
            curl_setopt($ch, CURLOPT_URL,$url);
            ob_start();
            curl_exec($ch);
            $result = ob_get_contents() ;
            ob_end_clean();
            if($result=="VERIFIED" && $payment_status=='Completed'){
                M('order')->where(array('order_id'=>$orderNumber))->setField('order_status',1);
                $this->paypal_log('订单支付成功');
            }else{
                $this->paypal_log('支付失败或校验不合格'.$result.'/'.$payment_status);
            }
            die();

        }



    }

    public function success(){
        $this->display();
    }
}

pay的view视图代码 ,success的视图就是一个成功返回页,随便弄了。

<html>
<body>
<form style="visibility:hidden" action="{$gateway}" id="paypal_standard_checkout" name="paypal_standard_checkout" method="POST">
    <input type="hidden" name="cmd" value="_xclick">
    <input type="hidden" name="business" value="{$business}">
    <input type="hidden" name="item_name" value="{$product_name}">
    <input type="hidden" name="amount" value="{$price}">
    <input type="hidden" name="currency_code" value="USD">
    <input type="hidden" name="return" value="{$return}">
    <input type="hidden" name="notify_url" value="{$notify_url}">
    <input type="hidden" name="invoice" value="{$order_number}">
    <input type="hidden" name="custom" value="{$user.mail}">
    <input type="hidden" name="item_number" value="{$order_number}">
    <input id="lc" name="lc" value="en_USA" type="hidden"/>
    <input id="charset" name="charset" value="utf-8" type="hidden"/>
</form>
<script type="text/javascript">document.getElementById("paypal_standard_checkout").submit();</script>
</body>
</html>

标签: paypal, 在线支付, thinkphp

非特殊说明,本博所有文章均为博主原创。

最新文章

发表评论