如果本文对你有用,请爱心点个赞,提高排名,帮助更多的人。谢谢大家!❤

如果解决不了,可以在文末进群交流。

如果对你有帮助的话麻烦点个【推荐】~最好还可以follow一下我的GitHub~感谢观看!

微信支付接口的成功调用,真的是我项目中一步步踩坑踩出来。微信的开发文档,别的我不知道,就看完支付接口来讲,真的是太简单了,并且很多关联的参数如何设置、校验、调用,都是没有关联的。微信支付作为各大移动支付方式之一,又不得不用。本文是我项目中自己写的代码,部分来自度娘,但是逻辑我已经搞通了。有些写的臃肿,望大家指正。希望各位能够快速上手并掌握实战"干货"。

/* 官方文档
签名生成的通用步骤如下: 第一步,设所有发送或者接收到的数据为集合M,将集合M内非空参数值的参数按照参数名ASCII码从小到大排序(字典序),使用URL键值对的格式(即key1=value1&key2=value2…)拼接成字符串stringA。
特别注意以下重要规则:
◆ 参数名ASCII码从小到大排序(字典序);
◆ 如果参数的值为空不参与签名;
◆ 参数名区分大小写;
◆ 验证调用返回或微信主动通知签名时,传送的sign参数不参与签名,将生成的签名与该sign值作校验。
◆ 微信接口可能增加字段,验证签名时必须支持增加的扩展字段 第二步,在stringA最后拼接上key得到stringSignTemp字符串,并对stringSignTemp进行MD5运算,再将得到的字符串所有字符转换为大写,得到sign值signValue。
◆ key设置路径:微信商户平台(pay.weixin.qq.com)-->账户设置-->API安全-->密钥设置
*/

提供几个大家项目中可能会用的文档

Demo下载: https://pay.weixin.qq.com/wiki/doc/api/app/app.php?chapter=11_1

API列表及各参数含义:https://pay.weixin.qq.com/wiki/doc/api/jsapi.php?chapter=9_1

废话不多说了,直接上代码,不懂地方可留言,或者进微信群内交流。群二维码如果过期,请加我微信:mengyilingjian.


<?php  

class Wxpay{
//modify by 墜夢 2018.07.11
public function wx_Pay($appid,$payDesc,$payAmount,$mch_id,$wxpay_key,$openid,$userid){
//准备参数
$nonce_str = $this->nonce_str(); //生成随机32位字符串
$out_trade_no = $this->order_number(); //生成订单号
$spbill_create_ip = $this->get_real_ip(); //获取支付ip
$trade_type = 'JSAPI'; //支付方式
$notify_url = "https://".$_SERVER['HTTP_HOST']."/********/paySuccess.php"; //支付成功的回调地址,不能携带参数,支付成功用来更新数据库插入订单的状态 //向数据库插入数据订单信息
$insertData=array();
$insertData['order_no'] = $out_trade_no; //订单编号
$insertData['user_id'] = $userid; //用户id
$insertData['pay_price'] = $payAmount; //支付金额
$insertData['order_status'] = 1;
$insertData['order_time'] = TIMESTAMP; //订单创建时间 $insertResult = DB::insert('*********',$insertData,$return_insert_id = true); //创建订单到数据库 if($insertResult > 0){ //数据库数据插入成功
//配置请求参数
//文档地址: https://pay.weixin.qq.com/wiki/doc/api/wxa/wxa_api.php?chapter=9_1&index=1
$payAmount = intval($payAmount)*100; //此处需注意接口中金额的单位为分
$signdata['appid'] = $appid; //小程序的appid
$signdata['body'] = $payDesc; //商品描述
$signdata['mch_id'] = $mch_id; //商户号请到后台配置查看
$signdata['nonce_str'] = $nonce_str; //随机字符串
$signdata['notify_url'] = $notify_url; //回调地址
$signdata['openid'] = $openid; //小程序openid
$signdata['out_trade_no'] = $out_trade_no; //自定义商户订单号规则
$signdata['spbill_create_ip'] = $spbill_create_ip; //获取用户id
$signdata['total_fee'] = $payAmount; //总金额
$signdata['trade_type'] = $trade_type; //交易类型 默认 $sign = $this->MakeSign($signdata,$wxpay_key); $stringXml = '<xml>
<appid>'.$appid.'</appid>
<body>'.$payDesc.'</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>'.$payAmount.'</total_fee>
<trade_type>'.$trade_type.'</trade_type>
<sign>'.$sign.'</sign>
</xml> '; $orderUrl = 'https://api.mch.weixin.qq.com/pay/unifiedorder'; //统一下单url接口
$xml = $this->http_request($orderUrl,$stringXml); //请求curl
$orderInfo = $this->xmlarray($xml);//将XML数据转成array // print_r($orderInfo);exit; //此处打开可查看接口是否走通 if(is_array($orderInfo) && $orderInfo['RETURN_CODE'] == 'SUCCESS' && $orderInfo['RESULT_CODE'] == 'SUCCESS'){
// echo 222;exit; //文档地址: https://pay.weixin.qq.com/wiki/doc/api/wxa/wxa_api.php?chapter=7_7&index=3
$tmp=array();//临时数组用于签名
$time = strval(time());
$tmp['appId'] = $appid;
$tmp['nonceStr'] = $nonce_str;
$tmp['package'] = 'prepay_id='.$orderInfo['PREPAY_ID'];
$tmp['signType'] = 'MD5';
$tmp['timeStamp'] = $time; //下单成功 回调地址 确认订单所需要返回的数据
$resData['paySign'] = $this->MakeSign($tmp,$wxpay_key);
$resData['timeStamp'] = $time;//时间戳
$resData['nonceStr'] = $nonce_str;//随机字符串
$resData['package'] = 'prepay_id='.$orderInfo['PREPAY_ID'];//统一下单接口返回的 prepay_id 参数值,提交格式如:prepay_id=*
$resData['signType'] = 'MD5';//签名算法,暂支持,MD5
$resData['out_trade_no'] = $out_trade_no; //前端需要的参数
$resData['state'] = 200;
$resData['text'] = "支付成功!";
}else{
$resData['state'] = 404;
$resData['text'] = "支付失败,请重试"; //接口支付失败
$resData['msg'] = $orderInfo['RETURN_MSG'];
}
echo json_encode($resData);
}else{
$resData['state'] = 400;
$resData['text'] = "系统繁忙,请重试"; //数据库数据插入失败
echo json_encode($resData);
}
exit;
} //随机32位字符串
private function nonce_str(){
$result = '';
$str = 'mengyilingjian890106zhuimeng8899';
for ($i=0;$i<32;$i++){
$result .= $str[rand(0,48)];
}
return $result;
} //生成商户订单号
private function order_number($tel){
$order_no = "JY".date("YmdHis")."-".mt_rand(111111, 666666);
return $order_no;//凑齐32位商户订单号,可自行定义
} //签名
private function MakeSign($params,$KEY){
//签名步骤一:按字典序排序数组参数
ksort($params);
$string = $this->ToUrlParams($params); //参数进行拼接key=value&k=v
//签名步骤二:在string后加入KEY
$string = $string . "&key=".$KEY;
//签名步骤三:MD5加密
$string = md5($string);
//签名步骤四:所有字符转为大写
$result = strtoupper($string);
return $result;
} //拼接api密钥
public function ToUrlParams( $params ){
$string = '';
if( !empty($params) ){
$array = array();
foreach( $params as $key => $value ){
$array[] = $key.'='.$value;
}
$string = implode("&",$array);
}
return $string;
} //获取用户ip地址
private function get_real_ip(){
if(getenv("HTTP_CLIENT_IP") && strcasecmp(getenv("HTTP_CLIENT_IP"), "unknow")){
$ip = getenv("HTTP_CLIENT_IP");
}else if(getenv("HTTP_X_FORWARDED_FOR") && strcasecmp(getenv("HTTP_X_FORWARDED_FOR"), "unknow")){
$ip = getenv("HTTP_X_FORWARDED_FOR");
}else if(getenv("REMOTE_ADDR") && strcasecmp(getenv("REMOTE_ADDR"), "unknow")){
$ip = getenv("REMOTE_ADDR");
}else if(isset($_SERVER["REMOTE_ADDR"]) && $_SERVER["REMOTE_ADDR"] && strcasecmp($_SERVER["REMOTE_ADDR"],"unknow")){
$ip = $_SERVER["REMOTE_ADDR"];
}else{
$ip = "unknow";
}
return $ip;
} //curl请求
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里面数据,转换成array
private function xmlarray($xml){
$p = xml_parser_create();
xml_parse_into_struct($p, $xml, $vals, $index);
xml_parser_free($p);
$data = "";
foreach ($index as $key=>$value) {
if($key == 'xml' || $key == 'XML') continue;
$tag = $vals[$value[0]]['tag'];
$value = $vals[$value[0]]['value'];
$data[$tag] = $value;
}
return $data;
} } //调用实例
$startPay = new Wxpay();
echo $startPay -> wx_Pay($appId,$payDesc,$payAmount,$mch_id,$wxpay_key,$openid,$userid); /*
参数说明:
$appId:开发者的appid;
$payDesc:支付的商品描述;
$payAmount:支付的商品价格,单位为分
$mch_id:支付的商户号;
$wxpay_key:开发者的支付key;
$openid:用户标识,用户登陆的openid;
$userid:支付者的身份标识
再看不懂请到顶部看我给的链接。
*/

微信支付接口--超详细带注释代码--Demo的更多相关文章

  1. 微信JS支付代码_前端调用微信支付接口

    转自:http://dditblog.com/itshare_553.html 跟大家分享一段微信支付的js代码片段.V3版的微信支付没有paySignKey参数.基本上是直接复制就可以使用了.改一改 ...

  2. 超详细的Xcode代码格式化教程,可自定义样式。

    超详细的Xcode代码格式化教程,可自定义样式. 为什么要格式化代码 当团队内有多人开发的时候,每个人写的代码格式都有自己的喜好,也可能会忙着写代码而忽略了格式的问题.在之前,我们可能会写完代码后,再 ...

  3. php微信支付接口开发程序

    php微信支付接口开发程序讲解 微信支付接口现在也慢慢的像支付宝一个可以利用api接口来实现第三方网站或应用进行支付了, 下文整理了一个php微信支付接口开发程序并且己测试,有兴趣的朋友可进入参考. ...

  4. JAVA微信支付接口开发——支付

    微信支付接口开发--支付 这几天在做支付服务,系统接入了支付宝.微信.银联三方支付接口.个人感觉支付宝的接口开发较为简单,并且易于测试. 关于数据传输,微信是用xml,所以需要对xml进行解析. 1. ...

  5. php微信支付接口开发程序(流程已通)

    php微信支付接口开发程序(流程已通) 来源:未知    时间:2014-12-11 17:11   阅读数:11843   作者:xxadmin [导读] 微信支付接口现在也慢慢的像支付宝一个可以利 ...

  6. 如何使用 RESTClient 调试微信支付接口

    我们知道微信支付使用http协议进行api调用,body 使用xml格式,使用的一般http在线调试工具,无法进行xml数据的post. RESTClient 做的很好,支持各种http 方法,bod ...

  7. 微信小程序PHP 微信支付接口调用

    小程序端 /** * 微信支付接口 */ wxPaymoney:function (out_trade_no, true_money){ //out_trade_no 后台统一下单接口需要用 var ...

  8. 关于微信支付接口,curl错误代码58

    微信支付接口,curl错误代码58 之前的微信付款到用户零钱都是好好的,今天运营来找我, 我想了了下,就是进行了网站搬家 看了下 微信支付相关的证书配置文件 知道了,在这个 要改下证书的路径 WxPa ...

  9. 微信支付接口,curl错误代码58

    微信支付接口,curl错误代码58 之前的微信付款到用户零钱都是好好的,今天运营来找我, 我想了了下,就是进行了网站搬家 看了下 微信支付相关的证书配置文件 知道了,在这个 要改下证书的路径 WxPa ...

随机推荐

  1. maven引入CDH依赖包

    1. POM文件加入仓库 注意:id要和仓库配置中的id一致. <repositories> <repository> <id>cloudera</id> ...

  2. Python3基础 tuple 使用格式化字符串进行输出

             Python : 3.7.3          OS : Ubuntu 18.04.2 LTS         IDE : pycharm-community-2019.1.3    ...

  3. 如何查看Linux服务器是32位还是64位?

    使用命令 “getconf LONG_BIT” 如果返回的是32,那么就是32位 如果返回的是64,那么就是64位

  4. aardio 文档

    aardio 文档 根据官方帮助手册制作了一份文档,添加了一些特性. 支持手机阅读 不用电脑也可以学习 aau 了,不受屏幕大小限制,你的小清新还是你的小清新~ 简单的搜索功能 快捷复制示例代码 基于 ...

  5. [LeetCode] 20. Valid Parentheses 合法括号

    Given a string containing just the characters '(', ')', '{', '}', '[' and ']', determine if the inpu ...

  6. 算法浅谈之DP悬线法

    悬线法 用途 解决给定矩阵中满足条件的最大子矩阵 做法 用一条线(横竖貌似都行)左右移动直到不满足约束条件或者到达边界 定义 \(left[i][j]\):代表从\((i,j)\)能到达的最左位置 \ ...

  7. 使用WinFrom + CefSharp 开发客户端程序

    今天使用CefSharp,加上本地资源文件嵌入了HTML.CSS.JS文件,做为Winform的UI:效果不错,漂亮可控,简简单单,半天时间搞定从开发到上线: 下面记录下相关的备忘: (窗口的效果) ...

  8. Mysql数据库索引IS NUll ,IS NOT NUll ,!= 是否走索引

    声明在前面 总结就是 不能单纯说 走和不走,需要看数据库版本,数据量等 ,希望不要引起大家的误会,也不要被标题党误导了. 1 数据库版本: 2 建表语句 CREATE TABLE s1 ( id IN ...

  9. hdu 2962 题解

    题目 题意 给出一张图,每条道路有限高,给出车子的起点,终点,最高高度,问在保证高度尽可能高的情况下的最短路,如果不存在输出 $ cannot  reach  destination $ 跟前面 $ ...

  10. FireDAC 中文字段过滤问题

    当使用 FireDAC Filter  过滤数据的时候,通常这样写: FDMemTable.Filtered := False; FDMemTable1.Filter := '姓名=' + strin ...