<?php /** * Created by PhpStorm. * User: ruidiudiu * Date: 2018/10/16 * Time: 16:34 */ namespace wxapp\pay; const APICLIENT_CERT=EXTEND_PATH."wxapp/pay/cert/apiclient_cert.pem"; const APICLIENT_KEY=EXTEND_PATH."wxapp/pay/cert/apiclient_key.pem"; class WecharGetCash{ protected $appid;//商户账号 protected $mch_id;//商户号 protected $key; protected $partner_trade_no;//商户订单号 protected $openid; protected $check_name;//校验用户姓名选项 NO_CHECK:不校验真实姓名 FORCE_CHECK:强校验真实姓名 protected $amount;//金额 protected $desc;//企业付款备注 protected $spbill_create_ip;//Ip地址:该IP同在商户平台设置的IP白名单中的IP没有关联,该IP可传用户端或者服务端的IP。 function __construct($openid,$partner_trade_no,$desc,$amount) { $this->appid = config('wechat_config.app_id'); $this->mch_id = config('wechat_config.payment')['merchant_id']; $this->key = config('wechat_config.payment')['key']; $this->partner_trade_no = $partner_trade_no;//商户订单号 $this->openid = $openid; $this->check_name = "NO_CHECK"; $this->amount = $amount*100;//金额 $this->desc = $desc;//企业付款备注 $this->spbill_create_ip = "114.215.223.17";//Ip地址 } public function getCash() { //提现接口 $return = $this->enterprisePayment(); return $return; } //企业付款接口 private function enterprisePayment() { $url = 'https://api.mch.weixin.qq.com/mmpaymkttransfers/promotion/transfers'; $parameters = array( 'mch_appid' => $this->appid, 'mchid' => $this->mch_id, 'nonce_str' => $this->createNoncestr(), 'partner_trade_no' => $this->partner_trade_no, 'openid' => $this->openid, 'check_name' => $this->check_name, 'amount' => $this->amount, 'desc' => $this->desc, 'spbill_create_ip' => $this->spbill_create_ip ); //签名 $parameters['sign'] = $this->getSign($parameters); $xmlData = $this->arrayToXml($parameters); $return = $this->xmlToArray($this->postXmlCurl($xmlData, $url, 60)); return $return; } private static function postXmlCurl($xml, $url, $second = 30) { $ch = curl_init(); //设置超时 curl_setopt($ch, CURLOPT_TIMEOUT, $second); curl_setopt($ch, CURLOPT_URL, $url); curl_setopt($ch, CURLOPT_SSL_VERIFYPEER, FALSE); curl_setopt($ch, CURLOPT_SSL_VERIFYHOST, FALSE); //严格校验 //第一种方法,cert 与 key 分别属于两个.pem文件 //默认格式为PEM,可以注释 curl_setopt($ch,CURLOPT_SSLCERT,APICLIENT_CERT); curl_setopt($ch,CURLOPT_SSLKEY,APICLIENT_KEY); //设置header curl_setopt($ch, CURLOPT_HEADER, FALSE); //要求结果为字符串且输出到屏幕上 curl_setopt($ch, CURLOPT_RETURNTRANSFER, TRUE); //post提交方式 curl_setopt($ch, CURLOPT_POST, TRUE); curl_setopt($ch, CURLOPT_POSTFIELDS, $xml); curl_setopt($ch, CURLOPT_CONNECTTIMEOUT, 20); curl_setopt($ch, CURLOPT_TIMEOUT, 40); set_time_limit(0); //运行curl $data = curl_exec($ch); //返回结果 if ($data) { curl_close($ch); return $data; } else { $error = curl_errno($ch); curl_close($ch); throw new ErrorException("curl出错,错误码:$error"); } } //数组转换成xml private function arrayToXml($arr) { $xml = "<root>"; foreach ($arr as $key => $val) { if (is_array($val)) { $xml .= "<" . $key . ">" . $this->arrayToXml($val) . "</" . $key . ">"; } else { $xml .= "<" . $key . ">" . $val . "</" . $key . ">"; } } $xml .= "</root>"; return $xml; } //xml转换成数组 public 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; } //作用:产生随机字符串,不长于32位 private 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; } //作用:生成签名 public function getSign($Obj) { foreach ($Obj as $k => $v) { $Parameters[$k] = $v; } //签名步骤一:按字典序排序参数 ksort($Parameters); $String = $this->formatBizQueryParaMap($Parameters, false); //签名步骤二:在string后加入KEY $String = $String . "&key=" . $this->key; //签名步骤三:MD5加密 $String = md5($String); //签名步骤四:所有字符转为大写 $result_ = strtoupper($String); return $result_; } ///作用:格式化参数,签名过程需要使用 private function formatBizQueryParaMap($paraMap, $urlencode) { $buff = ""; ksort($paraMap); foreach ($paraMap as $k => $v) { if(null != $v && "null" != $v && "sign" != $k) { if ($urlencode) { $v = urlencode($v); } $buff .= $k . "=" . $v . "&"; } } $reqPar=''; if (strlen($buff) > 0) { $reqPar = substr($buff, 0, strlen($buff) - 1); } return $reqPar; } }