APP微信支付php服务端函数方法
该代码编写于 thinkphp3.2框架,经过测试可行,有几个必要参数请自行修改!如有问题可联系本人 wx:xgaiych123
上代码
<?php
namespace wxPay\Controller;
use Think\Controller;
class AjaxpayfunController extends Controller {
function index(){
header('Content-Type:text/html;Charset=utf-8'); //php页面输出 乱码
//参数配置
$appid = '*********'; /*微信开放平台上的应用id*/
$mch_id = '*************'; /*微信申请成功之后邮件中的商户id*/
$api_key = '************************'; /*在微信商户平台上自己设定的api密钥 32位*/
$out_trade_no = $this -> ordersinfo(); /*商户订单号*/
$price = $_GET['total']*1; /*支付金额*/
$price = 0.02*1; /*支付金额*/
$code = $this -> weChatPay($out_trade_no,$price,$appid,$mch_id,$api_key);
echo($code);
}
//入口函数
function weChatPay($order_num,$price,$appid,$mch_id,$api_key){
$json = array();//生成预支付交易单的必选参数:
$newPara = array();//所需各项参数
$newPara["appid"] = $appid; //应用APP appid
$newPara["mch_id"] = $mch_id; //微信支付商户id//设备号
$newPara["device_info"] = $this -> createNoncestr(); //终端设备号(门店号或收银设备ID),如没有这里推荐使用函数生成随机字符串
$newPara["nonce_str"] = $this -> createNoncestr(); //随机字符串,不长于32位。推荐随机数生成算法
$newPara["body"] = "添美爱车"; //商品描述 或应用名称
$newPara["out_trade_no"] = $order_num; //商户订单号,这里是商户自己的内部的订单号
$newPara["total_fee"] = $price*100; //支付金额
$newPara["spbill_create_ip"] = $_SERVER["REMOTE_ADDR"]; //正在浏览当前页面用户的 IP 地址。
$newPara["notify_url"] = "http://**********/wxpay.php/Ajaxpayfun/wxpaynotify_url_sqlsta"; //支付成功后的回调地址注意,这里的url里面不要加参数
$newPara["trade_type"] = "APP"; //交易类型
$key = $api_key;// 密钥:在商户后台个人安全中心设置//第一次签名
$newPara["sign"] = $this -> appgetSign($newPara,$key);
//把数组转化成xml格式
$xmlData = $this -> arrayToXml($newPara);
$get_data = $this -> sendPrePayCurl($xmlData);
//返回的结果进行判断。
if($get_data["return_code"] == "SUCCESS" && $get_data["result_code"] == "SUCCESS"){
//根据微信支付返回的结果进行二次签名
//二次签名所需的随机字符串
$newPara["nonce_str"] = $this -> createNoncestr(); //二次签名所需的时间戳
$newPara["timeStamp"] = time().""; //二次签名剩余参数的补充
$secondSignArray = array(
"appid" =>$newPara["appid"],
"noncestr" =>$newPara["nonce_str"],
"package" =>"Sign=WXPay",
"prepayid" =>$get_data["prepay_id"],
"partnerid" =>$newPara["mch_id"],
"timestamp" =>$newPara["timeStamp"],);
$json["success"] = 1;
$json["ordersn"] = $newPara["out_trade_no"]; //订单号
$json["order_arr"] = $secondSignArray; //返给前台APP的预支付订单信息
$json["order_arr"]["sign"] = $this -> appgetSign($secondSignArray,$key); //预支付订单签名
$json["order_arr"]["out_trade_no"] = $newPara["out_trade_no"]; //商户订单号
$json["data"] = "预支付完成"; //预支付完成,在下方进行自己内部的业务逻辑
return json_encode($json["order_arr"]);
}else{
$json["success"] = 0;
$json["error"] =
$get_data["return_msg"];
return json_encode($json);
}
}
//商品订单号码生成方法可自定义
function ordersinfo(){
$shop = "TIANMEIAIC";
$date = date("YmdHi");
$time = time();
$out_trade_no = $shop.$date.$time;
return $out_trade_no;
}
//将数组转换为xml格式
function arrayToXml($arr){
$xml = "<xml>";
foreach ($arr as $key=>$val){
if (is_numeric($val)){
$xml.="<".$key.">".$val."</".$key.">";
}else{
$xml.="<".$key."><![CDATA[".$val."]]></".$key.">";
}
}
$xml.="</xml>";
return $xml;
}
//发送请求
function sendPrePayCurl($xml,$second=30){
$url = "https://api.mch.weixin.qq.com/pay/unifiedorder";
$ch = curl_init();
curl_setopt($ch,CURLOPT_URL, $url);
curl_setopt($ch,CURLOPT_SSL_VERIFYPEER,FALSE);
curl_setopt($ch,CURLOPT_SSL_VERIFYHOST,FALSE);//设置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
$data = curl_exec($ch);
curl_close($ch);
$data_xml_arr =$this -> XMLDataParse($data);
if($data_xml_arr){
return $data_xml_arr;
}else{
$error = curl_errno($ch);
echo"curl出错,错误码:$error"."<br>";
echo "<a href='http://curl.haxx.se/libcurl/c/libcurl-errors.html'>错误原因查询</a></br>";
curl_close($ch);
return false;
}
}
//xml格式数据解析函数
function XMLDataParse($data){
$xml = simplexml_load_string($data,NULL,LIBXML_NOCDATA);
$array=json_decode(json_encode($xml),true);
return $array;
}
//随机字符串
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;
}
/*格式化参数格式化成url参数 生成签名sign*/
function appgetSign($Obj,$appwxpay_key){
foreach ($Obj as $k => $v){
$Parameters[$k] = $v;
}
//签名步骤一:按字典序排序参数
ksort($Parameters);
$String = $this -> formatBizQueryParaMap($Parameters, false);
//echo "【string1】".$String."</br>";
//签名步骤二:在string后加入KEY
if($appwxpay_key){
$String = $String."&key=".$appwxpay_key;
}
//echo "【string2】".$String."</br>";
//签名步骤三:MD5加密
$String = md5($String);
//echo "【string3】 ".$String."</br>";
//签名步骤四:所有字符转为大写
$result_ = strtoupper($String);
//echo "【result】 ".$result_."</br>";
return $result_;
}
//按字典序排序参数
function formatBizQueryParaMap($paraMap, $urlencode) {
$buff = "";
ksort($paraMap);
foreach ($paraMap as $k => $v){
if($urlencode){
$v = urlencode($v);
}
//$buff .= strtolower($k) . "=" . $v . "&";
$buff .= $k . "=" . $v . "&";}
$reqPar;if (strlen($buff) > 0){
$reqPar = substr($buff, 0, strlen($buff)-1);
}
return $reqPar;
}
//微信支付成功后回调方法
public function wxpaynotify_url_sqlsta(){
$testxml = file_get_contents("php://input");
$jsonxml = json_encode(simplexml_load_string($testxml, 'SimpleXMLElement', LIBXML_NOCDATA));
$result = json_decode($jsonxml, true);//转成数组,
if($result){
//如果成功返回了
$out_trade_no = $result['out_trade_no'];
$transaction_id = $result['transaction_id'];
if($result['return_code'] == 'SUCCESS' && $result['result_code'] == 'SUCCESS'){
//执行业务逻辑改变订单状态等操作
$orderssave = $this -> orderssqlstasave($out_trade_no,$transaction_id);
}
}
}
//数据库订单数据修改方法
public function orderssqlstasave($out_trade_no,$transaction_id){
//查询创建订单表 where("out_trade_no='".$out_trade_no."' and paysta=1")
$where['paysta'] = 1;
$where['out_trade_no'] = $out_trade_no;
$list = M("orders") -> where($where) -> find();
if ($list && $list['transaction_id'] == '') {
$data['id'] = $list['id'];
$data['transaction_id'] = $transaction_id;
//查询出来有该订单 就改变状态
$save = M("orders") -> save($data);
if ($save) {
return $save;
}
}
}
}