微信小程序支付

统一下单

    //小程序微信支付 
    function WxPay($data)
    {
        $fee = $data['fee'];//金额
        $appid = "wxd1234567";//appid.
        $body = 'xxx小程序消费';
        $mch_id = '1234567';//商户号
        $nonce_str = $this->nonce_str();//随机字符串
        $notify_url = 'https://www.xxx.com/xxx/xxx/Api/wxnotifyurl';//回调的url,注:此处url必须是外网可访问地址才可以。
        $openid = $data['openid'];  //支付用户的openid
        $out_trade_no = $data['out_trade_no'];//商户订单号:需要保证随机生成不重复,建议生成20位
        $spbill_create_ip = get_client_ip();//服务器的ip;
        $total_fee = $fee*100;// 微信支付单位是分,所以这里需要*100
        $trade_type = 'JSAPI';//交易类型 默认
        //这里是按照顺序的 排序错误 肯定出错
        $post['appid'] = $appid;
        $post['body'] = $body;
        $post['mch_id'] = $mch_id;
        $post['nonce_str'] = $nonce_str;//随机字符串
        $post['notify_url'] = $notify_url;
        $post['openid'] = $openid;
        $post['out_trade_no'] = $out_trade_no;
        $post['spbill_create_ip'] = $spbill_create_ip;//终端的ip
        $post['total_fee'] = $total_fee;//总金额
        $post['trade_type'] = $trade_type;
        $sign = $this->sign($post);//签名
        $post_xml = '<xml>
           <appid>'.$appid.'</appid>
           <body>'.$body.'</body>
           <mch_id>'.$mch_id.'</mch_id>
           <nonce_str>'.$nonce_str.'</nonce_str>
           <notify_url>'.$notify_url.'</notify_url>
           <openid>'.$openid.'</openid>
           <out_trade_no>'.$out_trade_no.'</out_trade_no>
           <spbill_create_ip>'.$spbill_create_ip.'</spbill_create_ip>
           <total_fee>'.$total_fee.'</total_fee>
           <trade_type>'.$trade_type.'</trade_type>
           <sign>'.$sign.'</sign>
        </xml> ';
        //统一接口prepay_id
        $url = 'https://api.mch.weixin.qq.com/pay/unifiedorder';
        $xml = $this->http_request($url,$post_xml);
        $array = $this->xmlToArray($xml);
        if($array['return_code'] == 'SUCCESS' && $array['result_code'] == 'SUCCESS'){
            $time = time();
            $tempArr=array(
                'appId' => $appid,
                'nonceStr' => $nonce_str,
                'package' => 'prepay_id='.$array['prepay_id'],
                'signType' => 'MD5',
                'timeStamp' => "$time"
            );
            $data['state'] = 200;
            $data['timeStamp'] = "$time";//时间戳
            $data['nonceStr'] = $nonce_str;//随机字符串
            $data['signType'] = 'MD5';//签名算法,暂支持 MD5
            $data['package'] = 'prepay_id='.$array['prepay_id'];//统一下单接口返回的 prepay_id 参数值,提交格式如:prepay_id=*
            $data['paySign'] = $this->sign($tempArr);//签名,具体签名方案参见微信公众号支付帮助文档;
            $data['out_trade_no'] = $out_trade_no;

        }else{
            $data['state'] = 0;
            $data['text'] = "错误";
            $data['returnArr'] = $array;
        }
        //将此处的$data返回给小程序即可
        if($data['text']){
            return showData(array('data'=>$data,'msg'=>$data['text']));
        } else {
            return showData(array('data'=>$data,'msg'=>'获取微信支付成功'));
        }
    }

签名方法

    private function sign($data){
        $stringA = '';
        foreach ($data as $key=>$value){
            if(!$value) continue;
            if($stringA) $stringA .= '&'.$key."=".$value;
            else $stringA = $key."=".$value;
        }
        //微信商户key
        $wx_key = '123456789abcd';//申请支付后有给予一个商户账号和密码,登陆后自己设置的key
        $stringSignTemp = $stringA.'&key='.$wx_key;
        return strtoupper(md5($stringSignTemp));
    }

发起请求方法

    public function http_request($url,$data = null,$headers=array()){
        $curl = curl_init();
        if( count($headers) >= 1 ){
            curl_setopt($curl, CURLOPT_HTTPHEADER, $headers);
        }
        curl_setopt($curl, CURLOPT_URL, $url);
        curl_setopt($curl, CURLOPT_SSL_VERIFYPEER, FALSE);
        curl_setopt($curl, CURLOPT_SSL_VERIFYHOST, FALSE);
        if (!empty($data)){
            curl_setopt($curl, CURLOPT_POST, 1);
            curl_setopt($curl, CURLOPT_POSTFIELDS, $data);
        }
        curl_setopt($curl, CURLOPT_RETURNTRANSFER, 1);
        $output = curl_exec($curl);
        curl_close($curl);
        return $output;
    }

xml转数组

    private function xmlToArray($xml)
    {
        //禁止引用外部xml实体
        libxml_disable_entity_loader(true);
        $xmlstring = simplexml_load_string($xml, 'SimpleXMLElement', LIBXML_NOCDATA);
        $val = json_decode(json_encode($xmlstring), true);
        return $val;

    }

还有一种情况 就是比如微信退款返回的xml是这样的

HTTP\/1.1 200 OK\r\nServer: nginx\r\nDate: Tue, 11 Jan 2022 01:31:56 GMT\r\nContent-Type: text\/plain\r\nContent-Length: 849\r\nConnection: keep-alive\r\nKeep-Alive: timeout=8\r\n\r\n<xml><return_code><![CDATA[SUCCESS]]><\/return_code>\n<return_msg><![CDATA[OK]]><\/return_msg>\n<appid><![CDATA[wxd325fc4]]><\/appid>\n<mch_id><![CDATA[1600642848]]><\/mch_id>\n<nonce_str><![CDATA[dDAQVtbSp2Qj]]><\/nonce_str>\n<sign><![CDATA[9DFDB6D3A87F659E6F0391A59]]><\/sign>\n<result_code><![CDATA[SUCCESS]]><\/result_code>\n<transaction_id><![CDATA[42000012972025613]]><\/transaction_id>\n<out_trade_no><![CDATA[1641863848526]]><\/out_trade_no>\n<out_refund_no><![CDATA[1641863676518]]><\/out_refund_no>\n<refund_id><![CDATA[50300800332022011306196]]><\/refund_id>\n<refund_channel><![CDATA[]]><\/refund_channel>\n<refund_fee>105<\/refund_fee>\n<coupon_refund_fee>0<\/coupon_refund_fee>\n<total_fee>150<\/total_fee>\n<cash_fee>150<\/cash_fee>\n<coupon_refund_count>0<\/coupon_refund_count>\n<cash_refund_fee>105<\/cash_refund_fee>\n<\/xml>

会有http这些信息,需要截取一下再用上面的代码处理

$xml = '<xml>'.explode('<xml>', $xml)[1];

然后再转数组

回调


    public function notifyWx(){
        //获取接口数据,如果$_REQUEST拿不到数据,则使用file_get_contents函数获取
        $post = $_REQUEST;
        Log::write('微信小程序回调 post_data'.$post);
        if ($post == null) {
            $post = file_get_contents("php://input");
        }
        if ($post == null) {
            $post = isset($GLOBALS['HTTP_RAW_POST_DATA']) ? $GLOBALS['HTTP_RAW_POST_DATA'] : '';
        }
        if (empty($post) || $post == null || $post == '') {
            //阻止微信接口反复回调接口  文档地址 https://pay.weixin.qq.com/wiki/doc/api/H5.php?chapter=9_7&index=7,必须!!!
            $str='<xml><return_code><![CDATA[SUCCESS]]></return_code><return_msg><![CDATA[OK]]></return_msg></xml>';
            echo $str;
            exit('Notify 非法回调');
        }

        libxml_disable_entity_loader(true); //禁止引用外部xml实体
        $xml = simplexml_load_string($post, 'SimpleXMLElement', LIBXML_NOCDATA);//XML转数组
        $post_data = (array)$xml;
        //可以将用户支付信息记录日志文件

        //后面是业务操作代码...
 		//......
 		//业务代码结束
        //阻止微信接口反复回调接口  文档地址 https://pay.weixin.qq.com/wiki/doc/api/H5.php?chapter=9_7&index=7,必须!!!
        $str='<xml><return_code><![CDATA[SUCCESS]]></return_code><return_msg><![CDATA[OK]]></return_msg></xml>';
        echo $str;
    }
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值