php中文网 | cnphp.com

 找回密码
 立即注册

QQ登录

只需一步,快速开始

搜索
查看: 321|回复: 0

微信支付PHP服务端案例,实现APP或小程序接口调用支付接口

[复制链接]

3138

主题

3148

帖子

1万

积分

管理员

Rank: 9Rank: 9Rank: 9

UID
1
威望
0
积分
7946
贡献
0
注册时间
2021-4-14
最后登录
2024-11-21
在线时间
763 小时
QQ
发表于 2024-2-17 22:03:18 | 显示全部楼层 |阅读模式
  1. <?php
  2. header("Content-type: text/html; charset=utf-8");
  3. $orderBody = "test商品";
  4. $tade_no = "abc_" . time();
  5. $total_fee = 1;
  6. $WxPayHelper = new WxPayHelper();
  7. $response = $WxPayHelper->getPrePayOrder($orderBody, $tade_no, $total_fee);
  8.         echo "<pre>";
  9.         print_r($response);
  10.         echo "</pre>";
  11.         

  12. /**
  13. * convert xml string to php array - useful to get a serializable value
  14. *
  15. * @param string $xmlstr
  16. * @return array
  17. * @author Adrien aka Gaarf
  18. */

  19. class WxPayHelper{
  20.     /*
  21.     配置参数
  22.     */
  23.     var $config = array(
  24.         'appid' => "wxb96ecb1e787528b2",    /*微信开放平台上的应用id*/
  25.         'mch_id' => "1419216902",   /*微信申请成功之后邮件中的商户id*/
  26.         'api_key' => "dNOnNIu13zShL9FsF0c48NxRHwKGlUnS",    /*在微信商户平台上自己设定的api密钥 32位*/
  27.         'notify_url' => 'www.chaokongs.com' /*自定义的回调程序地址id*/
  28.     );

  29.     public function  __construct() {

  30.     }

  31.     //获取预支付订单
  32.     public function getPrePayOrder($body, $out_trade_no, $total_fee){
  33.         $url = "https://api.mch.weixin.qq.com/pay/unifiedorder";
  34.         $notify_url = $this->config["notify_url"];

  35.         $onoce_str = $this->getRandChar(32);

  36.         $data["appid"] = $this->config["appid"];
  37.         $data["body"] = $body;
  38.         $data["mch_id"] = $this->config['mch_id'];
  39.         $data["nonce_str"] = $onoce_str;
  40.         $data["notify_url"] = $notify_url;
  41.         $data["out_trade_no"] = $out_trade_no;
  42.         $data["spbill_create_ip"] = $this->get_client_ip();
  43.         $data["total_fee"] = $total_fee;
  44.         $data["trade_type"] = "APP";
  45.         $s = $this->getSign($data, false);
  46.         $data["sign"] = $s;

  47.         $xml = $this->arrayToXml($data);
  48.         $response = $this->postXmlCurl($xml, $url);

  49.         //将微信返回的结果xml转成数组
  50.         return $this->xmlstr_to_array($response);
  51.     }

  52.     //执行第二次签名,才能返回给客户端使用
  53.     public function getOrder($prepayId){
  54.         $data["appid"] = $this->config["appid"];
  55.         $data["noncestr"] = $this->getRandChar(32);;
  56.         $data["package"] = "Sign=WXPay";
  57.         $data["partnerid"] = $this->config['mch_id'];
  58.         $data["prepayid"] = $prepayId;
  59.         $data["timestamp"] = time();
  60.         $s = $this->getSign($data, false);
  61.         $data["sign"] = $s;

  62.         return $data;
  63.     }

  64.     /*
  65.         生成签名
  66.     */
  67.     function getSign($Obj)
  68.     {
  69.         foreach ($Obj as $k => $v)
  70.         {
  71.             $Parameters[strtolower($k)] = $v;
  72.         }
  73.         //签名步骤一:按字典序排序参数
  74.         ksort($Parameters);
  75.         $String = $this->formatBizQueryParaMap($Parameters, false);
  76.         //echo "【string】 =".$String."</br>";
  77.         //签名步骤二:在string后加入KEY
  78.         $String = $String."&key=".$this->config['api_key'];
  79.       
  80.         //签名步骤三:MD5加密
  81.         $result_ = strtoupper(md5($String));
  82.         return $result_;
  83.     }

  84.     //获取指定长度的随机字符串
  85.     function getRandChar($length){
  86.        $str = null;
  87.        $strPol = "ABCDEFGHIJKLMNOPQRSTUVWXYZ0123456789abcdefghijklmnopqrstuvwxyz";
  88.        $max = strlen($strPol)-1;

  89.        for($i=0;$i<$length;$i++){
  90.         $str.=$strPol[rand(0,$max)];//rand($min,$max)生成介于min和max两个数之间的一个随机整数
  91.        }

  92.        return $str;
  93.     }

  94.     //数组转xml
  95.     function arrayToXml($arr)
  96.     {
  97.         $xml = "<xml>";
  98.         foreach ($arr as $key=>$val)
  99.         {
  100.              if (is_numeric($val))
  101.              {
  102.                 $xml.="<".$key.">".$val."</".$key.">";

  103.              }
  104.              else
  105.                 $xml.="<".$key."><![CDATA[".$val."]]></".$key.">";  
  106.         }
  107.         $xml.="</xml>";
  108.         return $xml;
  109.     }

  110.     //post https请求,CURLOPT_POSTFIELDS xml格式
  111.     function postXmlCurl($xml,$url,$second=30)
  112.     {      
  113.         //初始化curl        
  114.         $ch = curl_init();
  115.         //超时时间
  116.         curl_setopt($ch,CURLOPT_TIMEOUT,$second);
  117.         //这里设置代理,如果有的话
  118.         //curl_setopt($ch,CURLOPT_PROXY, '8.8.8.8');
  119.         //curl_setopt($ch,CURLOPT_PROXYPORT, 8080);
  120.         curl_setopt($ch,CURLOPT_URL, $url);
  121.         curl_setopt($ch,CURLOPT_SSL_VERIFYPEER,FALSE);
  122.         curl_setopt($ch,CURLOPT_SSL_VERIFYHOST,FALSE);
  123.         //设置header
  124.         curl_setopt($ch, CURLOPT_HEADER, FALSE);
  125.         //要求结果为字符串且输出到屏幕上
  126.         curl_setopt($ch, CURLOPT_RETURNTRANSFER, TRUE);
  127.         //post提交方式
  128.         curl_setopt($ch, CURLOPT_POST, TRUE);
  129.         curl_setopt($ch, CURLOPT_POSTFIELDS, $xml);
  130.         //运行curl
  131.         $data = curl_exec($ch);
  132.         //返回结果
  133.         if($data)
  134.         {
  135.             curl_close($ch);
  136.             return $data;
  137.         }
  138.         else
  139.         {
  140.             $error = curl_errno($ch);
  141.             echo "curl出错,错误码:$error"."<br>";
  142.             echo "<a href='http://curl.haxx.se/libcurl/c/libcurl-errors.html'>错误原因查询</a></br>";
  143.             curl_close($ch);
  144.             return false;
  145.         }
  146.     }

  147.     /*
  148.         获取当前服务器的IP
  149.     */
  150.     function get_client_ip()
  151.     {
  152.         if ($_SERVER['REMOTE_ADDR']) {
  153.         $cip = $_SERVER['REMOTE_ADDR'];
  154.         } elseif (getenv("REMOTE_ADDR")) {
  155.         $cip = getenv("REMOTE_ADDR");
  156.         } elseif (getenv("HTTP_CLIENT_IP")) {
  157.         $cip = getenv("HTTP_CLIENT_IP");
  158.         } else {
  159.         $cip = "unknown";
  160.         }
  161.         return $cip;
  162.     }

  163.     //将数组转成uri字符串
  164.     function formatBizQueryParaMap($paraMap, $urlencode)
  165.     {
  166.         $buff = "";
  167.         ksort($paraMap);
  168.         foreach ($paraMap as $k => $v)
  169.         {
  170.             if($urlencode)
  171.             {
  172.                $v = urlencode($v);
  173.             }
  174.             $buff .= strtolower($k) . "=" . $v . "&";
  175.         }
  176.         $reqPar;
  177.         if (strlen($buff) > 0)
  178.         {
  179.             $reqPar = substr($buff, 0, strlen($buff)-1);
  180.         }
  181.         return $reqPar;
  182.     }

  183.     /**xml转成数组*/
  184.    
  185.    
  186.     function xmlstr_to_array($xmlstr) {
  187.       $doc = new DOMDocument();
  188.       $doc->loadXML($xmlstr);
  189.       return $this->domnode_to_array($doc->documentElement);
  190.     }
  191.     function domnode_to_array($node) {
  192.       $output = array();
  193.       switch ($node->nodeType) {
  194.        case XML_CDATA_SECTION_NODE:
  195.        case XML_TEXT_NODE:
  196.         $output = trim($node->textContent);
  197.        break;
  198.        case XML_ELEMENT_NODE:
  199.         for ($i=0, $m=$node->childNodes->length; $i<$m; $i++) {
  200.          $child = $node->childNodes->item($i);
  201.          $v = $this->domnode_to_array($child);
  202.          if(isset($child->tagName)) {
  203.            $t = $child->tagName;
  204.            if(!isset($output[$t])) {
  205.             $output[$t] = array();
  206.            }
  207.            $output[$t][] = $v;
  208.          }
  209.          elseif($v) {
  210.           $output = (string) $v;
  211.          }
  212.         }
  213.         if(is_array($output)) {
  214.          if($node->attributes->length) {
  215.           $a = array();
  216.           foreach($node->attributes as $attrName => $attrNode) {
  217.            $a[$attrName] = (string) $attrNode->value;
  218.           }
  219.           $output['@attributes'] = $a;
  220.          }
  221.          foreach ($output as $t => $v) {
  222.           if(is_array($v) && count($v)==1 && $t!='@attributes') {
  223.            $output[$t] = $v[0];
  224.           }
  225.          }
  226.         }
  227.        break;
  228.       }
  229.       return $output;
  230.     }
  231. }
  232. ?>
复制代码

回复

使用道具 举报

您需要登录后才可以回帖 登录 | 立即注册

本版积分规则

QQ|php中文网 | cnphp.com ( 赣ICP备2021002321号-2 )

GMT+8, 2024-11-21 21:46 , Processed in 1.056217 second(s), 41 queries , Gzip On.

Powered by Discuz! X3.4 Licensed

Copyright © 2001-2020, Tencent Cloud.

申明:本站所有资源皆搜集自网络,相关版权归版权持有人所有,如有侵权,请电邮(fiorkn@foxmail.com)告之,本站会尽快删除。

快速回复 返回顶部 返回列表