微信小程序之wx.requestPayment 發起微信支付


wx.requestPayment 發起微信支付

timeStamp 時間戳

nonceStr 隨機字符串

package 統一下單接口返回的 prepay_id 參數值

signType 簽名算法

paySign 支付簽名

success 接口成功回調

fail 接口失敗回調

complete 接口完成回調(成功,失敗都執行)

1.先調用后台接口,生產基本數據

// 獲取店鋪信息
Api.BalancePay({
    openid: openid,
    amount: amount,
    bid: bid,
}).then(res => {
    if (res.errno) {
        wx.showToast({ title: res.errdesc });
        return;
    }
    var data = res.data;
    ...
})

具體的這個是做什么的呢?

判斷用戶是否存在。

判斷充值id是否存在。

判斷充值金額是否合法。

創建充值訂單。

創建統一支付訂單。

public function unifiedorder($openid,$order_num,$total_fee,$products_name){
        $trade_no = $order_num;
        $url = 'https://api.mch.weixin.qq.com/pay/unifiedorder';
        $data = [
            'appid'             => C('APPID'),
            'mch_id'            => C('MCHID'),
            'nonce_str'         => $this->createNonceStr(),
            'sign_type'         => 'MD5',
            'body'              =>  $products_name,  //商品名稱組合
            'attach'            => C('PAY_ATTACH_NAME'),
            'out_trade_no'      => $trade_no,        //訂單號
            'fee_type'          => 'CNY',
            'total_fee'         => $total_fee,
            'spbill_create_ip'  => $_SERVER['REMOTE_ADDR'],
            'goods_tag'         => C('PAY_ATTACH_NAME'),
            'notify_url'        => 'https://a.squmo.com/'.C('PAY_URL_NAME').'/Recharge/order_notice',
            'trade_type'        => 'JSAPI',
            'openid'            => $openid
        ];

        // 獲取簽名
       $sign = $this->MakeSign($data);
       $data['sign'] = $sign;
       $xml = $this->ToXml($data);
       vendor('Func.Http');
       // 提交獲取數據
       $result = $this->FromXml(Http::postXmlCurl($url,$xml));
       return $result;
}

一切准備就緒之后,將一些數據返回給小程序。

$unifiedorder = $this->unifiedorder($openid,$order_num,$total_price,$products_name);
$data = [
    'appId'     => C('APPID'),
    'timeStamp' => time(),
    'nonceStr'  => $this->createNonceStr(),
    'package'   => 'prepay_id='.$unifiedorder['prepay_id'],
    'signType'  => 'MD5'
];
// 獲取簽名
$sign = $this->MakeSign($data);
$data['sign'] = $sign;
$this->json->setAttr('data',$data);
$this->json->Send();

2.再發起微信支付

wx.requestPayment({
        'timeStamp': data.timeStamp.toString(),
        'nonceStr': data.nonceStr,
        'package': data.package,
        'signType': 'MD5',
        'paySign': data.sign,
        'success': function (res) {
            console.log('支付成功');
        },
        'fail': function (res) {
            console.log('支付失敗');
            return;
        },
        'complete': function (res) {
            console.log('支付完成');
            var url = that.data.url;
            console.log('get url', url)
            if (res.errMsg == 'requestPayment:ok') {
                wx.showModal({
                    title: '提示',
                    content: '充值成功'
                });
                if (url) {
                    setTimeout(function () {
                        wx.redirectTo({
                            url: '/pages' + url
                        });
                    }, 2000)
                } else {
                    setTimeout(() => {
                        wx.navigateBack()
                    }, 2000)
                }
            }
            return;
        }
});

3.支付成功的回調(異步操作)

//微信支付回調
public function order_notice(){
    // 微信公眾平台推送過來的post數據
    $xml = $GLOBALS['HTTP_RAW_POST_DATA'];
    // 獲取數據
    $data = $this->FromXml($xml);
    // 保存微信服務器返回的簽名sign
    $data_sign = $data['sign'];
    // sign不參與簽名算法
    unset($data['sign']);

    $sign = $this->makeSign($data);
    // 判斷簽名是否正確  判斷支付狀態
    if ( ($sign===$data_sign) && ($data['return_code']=='SUCCESS') && ($data['result_code']=='SUCCESS') ) {
        $result = $data;
        //獲取服務器返回的數據
        $order_num = $data['out_trade_no'];         //訂單單號
        $openid = $data['openid'];                  //付款人openID
        $total_fee = $data['total_fee'];            //付款金額
        $transaction_id = $data['transaction_id'];  //微信支付流水號
        $user = M('user');
        $user_flag = $user->where(array('openid'=>$openid))->find();
        $save_data = array(
            'total_payed_price' =>  $total_fee,     //實際到帳金額
            'transaction_id'    =>  $transaction_id,
            'paytime'           =>  time(),
            'status'            =>  2       //1未支付;2已支付;3已申請退款;4已退款;5已完成
        );
        $recharge = M('recharge');
        $recharge_flag=$recharge->where(array('recoder'=>$order_num,'uid'=>$user_flag['id']))->find();
        $recharge_amount=$recharge_flag['amount'];
        $recharge_save_flag =$recharge->where(array('recoder'=>$order_num,'uid'=>$user_flag['id']))->save($save_data);
        if($recharge_save_flag){
            $save_balance['balance']= $user_flag['balance']+$recharge_amount;
            $result_balance =$user->where(array('openid'=>$openid))->save($save_balance);
        }
    }else{
        $result = false;
    }
    // 返回狀態給微信服務器
    if ($result) {
        $str='<xml><return_code><![CDATA[SUCCESS]]></return_code><return_msg><![CDATA[OK]]></return_msg></xml>';
    }else{
        $str='<xml><return_code><![CDATA[FAIL]]></return_code><return_msg><![CDATA[簽名失敗]]></return_msg></xml>';
    }
    echo $str;
    return $result;
}

其他常用函數

	public function FromXml($xml)
    {
        if(!$xml){
            throw new WxPayException("xml數據異常!");
        }
        //將XML轉為array
        //禁止引用外部xml實體
        libxml_disable_entity_loader(true);
        $this->values = json_decode(json_encode(simplexml_load_string($xml, 'SimpleXMLElement', LIBXML_NOCDATA)), true);
        return $this->values;
    }

    public function ToXml($array){
        if(!is_array($array)|| count($array) <= 0){
           return ;
        }
        $xml = '<xml version="1.0">';
        foreach ($array as $key=>$val){
            if (is_numeric($val)){
              $xml.="<".$key.">".$val."</".$key.">";
            }else{
                $xml.="<".$key."><![CDATA[".$val."]]></".$key.">";
            }
        }
        $xml.="</xml>";
        return $xml;
    }

    private function MakeSign($data)
    {
        //簽名步驟一:按字典序排序參數
        ksort($data);
        $string = $this->ToUrlParams($data);
        //簽名步驟二:在string后加入KEY
        $string = $string . "&key=".C('WEIXIN_PAY_KEY');
        //簽名步驟三:MD5加密
        $string = md5($string);
        //簽名步驟四:所有字符轉為大寫
        $result = strtoupper($string);
        return $result;
    }

    private function ToUrlParams($array)
    {
        $buff = "";
        foreach ($array as $k => $v)
        {
            if($k != "sign" && $v != "" && !is_array($v)){
                $buff .= $k . "=" . $v . "&";
            }
        }
        $buff = trim($buff, "&");
        return $buff;
    }


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM