1500字范文,内容丰富有趣,写作好帮手!
1500字范文 > PHP使用Laravel-Pay组件快速接入微信JSAPI支付(微信公众号支付)

PHP使用Laravel-Pay组件快速接入微信JSAPI支付(微信公众号支付)

时间:2021-03-18 08:50:17

相关推荐

PHP使用Laravel-Pay组件快速接入微信JSAPI支付(微信公众号支付)

PHP使用Laravel-Pay组件快速接入微信JSAPI支付(微信公众号支付)

本文为系列文章,接下来分别会讲解如何接入微信 与 支付宝 支付并完成支付的保姆式教程,各支付代码示例细节详见页尾链接。


文章目录

PHP使用Laravel-Pay组件快速接入微信JSAPI支付(微信公众号支付)前言一、前期准备与花费明细(仅供参考)二、支付类型1.微信公众号支付(JSAPI支付)支付原理:前端html支付示例后端PHP拉起支付以及用户支付成功后异步回调示例 微信官方后台

前言

本篇介绍微信 H5、JSAPI(公众号)、APP、小程序支付、Native支付(手机扫网站二维码进行支付)、需要的基础资料


一、前期准备与花费明细(仅供参考)

注意:

这里必须要开通的是微信商户平台。剩下的更你的实际业务需求进行开通。

使用composer下载laravel-pay组件

composer require yansongda/pay -vvv

laravel-pay官网地址:/docs/v2/installation.html

laravel-pay Git项目地址:/yansongda/pay/tree/v2

二、支付类型

1.微信公众号支付(JSAPI支付)

支付原理:

1.前端获取微信code2.前端发送code到我方后台换openid3.带着openid请求我方后台拉起支付4.前端更具后台返回值判断是否拉起 微信付款页面5.用户在手机上进行付款操作6.用户付款结束后,微信服务器向我方服务器发送请求,告诉我们用户已经支付完了7.我方后台通过支付完成异步回调修改数据库中的订单支付状态值。8.End

代码如下(示例):

前端html支付示例

<!doctype html><html lang="en"><head><meta charset="UTF-8"><meta name="viewport"content="width=device-width, user-scalable=no, initial-scale=1.0, maximum-scale=1.0, minimum-scale=1.0"><meta http-equiv="X-UA-Compatible" content="ie=edge"><title>Document</title></head><body><button onclick="wechatPay()">点我拉起微信支付</button></body><script src="/ajax/libs/jquery/3.5.1/jquery.js"></script><script>var code = getQueryVariable('code');//微信支付codevar openid;//微信openid//1.先看地址栏中是否存在微信给的code//微信支付if(code){//有则直接用code后端换openid$.ajax({type : "POST", //提交方式url : "http://请求后端获取openid路由地址",//路径data : {'_token':"{{ csrf_token() }}",//laravel防止419错误的'code':code//微信的code},//数据,这里使用的是Json格式进行传输success : function(result) {//返回数据根据结果进行相应的处理open_id= result.data.openid;//设置openid//console.log(result.data.openid);}});}else{//没有则先获取公众号 codevar appid = "公众号appid";//这里填公众号appidvar redirect_uri = "填获取code后重定向的地址";//授权后重定向的回调链接地址, 请使用 urlEncode 对链接进行处理,例如:使用php urlencode(/test?order_id=1&user_id=18)var state = '';//重定向后会带上state参数,开发者可以填写a-zA-Z0-9的参数值,最多128字节;var url = "https://open./connect/oauth2/authorize?appid="+ appid +"&redirect_uri="+ redirect_uri +"&response_type=code&scope=snsapi_base&state="+ state +"#wechat_redirect";window.location.href = url;//重定向跳转,跳转完成后你会得到code}/*** 截取网址参数方法* 用于获取微信code* */function getQueryVariable(variable){var query = window.location.search.substring(1);var vars = query.split("&");for (var i=0;i<vars.length;i++) {var pair = vars[i].split("=");if(pair[0] == variable){return pair[1];}}return(false);}//请求后台微信支付接口获取支付必要参数function wechatPay() {if(!open_id){alert('500:获取openid失败');return false;}$.ajax({type : "POST", //提交方式url : "请求我方后台接口,向微信服务器发起支付请求wechatPay.php",//路径data : {'_token':"{{ csrf_token() }}",//解决laravel 419错误"open_id" : open_id,//用户openid},//数据,这里使用的是Json格式进行传输success : function(res) {//返回数据根据结果进行相应的处理//检测请求是否处理成功if (res.success) {//拉起微信APP支付(93-99行官方原代码,无需改动)if (typeof WeixinJSBridge == "undefined"){if( document.addEventListener ){document.addEventListener('WeixinJSBridgeReady', onBridgeReady, false);}else if (document.attachEvent){document.attachEvent('WeixinJSBridgeReady', onBridgeReady);document.attachEvent('onWeixinJSBridgeReady', onBridgeReady);}}else{onBridgeReady(res.data);//拉起微信客户端支付,官方代码,请勿随意修改}}//判断是否显示提示信息if(res.show_msg){alert(res.msg)}}});}//拉起微信客户端支付,官方代码,请勿随意修改function onBridgeReady(data){WeixinJSBridge.invoke('getBrandWCPayRequest', {"appId":data.appId,//公众号名称,由商户传入"timeStamp":data.timeStamp, //时间戳,自1970年以来的秒数"nonceStr":data.nonceStr, //随机串"package":data.package,"signType":data.signType, //微信签名方式:"paySign":data.paySign //微信签名},function(res){if(res.err_msg == "get_brand_wcpay_request:ok" ){// 使用以上方式判断前端返回,微信团队郑重提示://res.err_msg将在用户支付成功后返回ok,但并不保证它绝对可靠。//这里处理支付成功后的逻辑,通常为页面跳转window.location = "访问我方自主查询支付结果页面";//因为微信支付的同步回调结果不一定准确,所以我们需要自己主动再去查询一下用户是否已经支付成功,当然你也可以跳转到你希望跳转的页面}});}</script></html>

后端PHP拉起支付以及用户支付成功后异步回调示例

<?phpnamespace App\Http\Controllers\H5;use Illuminate\Http\Request;use App\Http\Controllers\Controller;use Yansongda\Pay\Log;use Yansongda\Pay\Pay;/*** 微信支付控制器* Class wechatPayController* @package App\Http\Controllers\H5* @todo 这里使用的laravel-pay 为2.x版本*/class WechatPayController extends Controller{private $wechatPay = ['appid' => '', // APP APPID(微信开发平台上的APP应用的appid,这个是接APP支付用的)'app_id' => '这里填公众号 APPID', // 公众号APPID'app_secret' => '这里填公众号开发者密码AppSecret', //公众号开发者密码AppSecret(这个支付用不到,是获取微信openid用的)'miniapp_id' => '', // 小程序 APPID'mch_id' => '微信商户平台的商户号',//商户号(不管是何种类型的支付,这个都是必填的)'key' => '商户平台的商户号秘钥',//商户号秘钥(不管是何种类型的支付,这个都是必填的)'notify_url' => '/wechatPay/wechatPayNotify',//微信小程序支付异步回调 @todo 上线的时候吧测试域名改为正式服务器的域名 (https://) 这里就写当前“WechatPayController”控制器的访问链接,注意定义路由动作时使用any,不用使用get或post,因为你不知道微信会用什么方式请求异步回调的控制器'cert_client' => './cert/apiclient_cert.pem', // optional,退款等情况时用到'cert_key' => './cert/apiclient_key.pem',// optional,退款等情况时用到'log' => [ // optional'file' => './login/wechat.log',//微信支付日志的log文件路径(文件会在 项目根目录/public/login/wechat.log)'level' => 'debug', // 建议生产环境等级调整为 info,开发环境为 debug(这个改不改都不会影响用户付钱)'type' => 'single', // optional, 可选 daily.'max_file' => 30, // optional, 当 type 为 daily 时有效,默认 30 天],'http' => [ // optional'timeout' => 5.0,'connect_timeout' => 5.0,// 更多配置项请参考 [Guzzle](https://guzzle-cn.readthedocs.io/zh_CN/latest/request-options.html)],// 'mode' => 'dev', // optional, dev/hk;当为 `hk` 时,为香港 gateway。];/*** 公共返回数据方法*/protected function send($code = 200,$success = false,$show_msg = false,$msg = '',$data=[]){return ['code' => $code,//状态码'success' => $success,//请求是否成功 true:成功,false:失败'show_msg' => $show_msg,//是否显示提示信息 true:是,false:否'msg' => $msg,//提示信息'data' => $data//返回数据数组];//返回数据}/*** 微信公众号支付(JSAPI支付)* @param Request $request*/public function wechatMpPay(Request $request){$open_id = $request->open_id;//微信openid$order_pay = ['openid' => $open_id,'out_trade_no' => time(),//我方订单号'total_fee' => 1, // **单位:分**测试专用'body' => '支付测试Demo',];$pay = Pay::wechat($this->wechatPay)->mp($order_pay);//拉起微信JSAPI支付if($pay){return $this->send(200,true,false,'成功',$pay);}return $this->send(500,false,false,'支付接口异常');}/*** 微信APP/小程序支付/拉起微信JSAPI支付/H5支付(支付后回调)* @return string*/public function wechatPayNotify(){$pay = Pay::wechat($this->wechatPay);try {$data = $pay->verify(); // 是的,验签就这么简单!返回值为微信回调的订单数据Log::debug('Wechat notify', $data->all());//记录日志file_put_contents('wechat_log.txt',$data->all());//判断是否支付成功if ($data->return_code == "SUCCESS" && $data->result_code == "SUCCESS") {//支付成功file_put_contents('wechat_log.txt','支付成功啦!');//这里你可以写判断订单是否已经改为支付状态,防止微信服务器因为首次异步不成功导致微信异步回调重复修改数据库!//告知微信服务器停止异步回调$str = '<xml><return_code><![CDATA[SUCCESS]]></return_code><return_msg><![CDATA[OK]]></return_msg></xml>';return $str;// laravel 框架中请直接 `return $pay->success()`}} catch (\Exception $exception) {Log::debug('Wechat BUG', $exception->getMessage());file_put_contents('wechat_log.txt','支付回调异常:'.$exception->getMessage());}$str = '<xml><return_code><![CDATA[SUCCESS]]></return_code><return_msg><![CDATA[OK]]></return_msg></xml>';return $str;// laravel 框架中请直接 `return $pay->success()`//return $pay->success()->send();// laravel 框架中请直接 `return $pay->success()`}/*** 检测订单支付是否成功* @param $order_id 订单id(orders表id)* @return \Illuminate\Contracts\View\Factory|\Illuminate\Http\RedirectResponse|\Illuminate\View\View*/public function isPaySuccess($order_id){//查询订单是否支付成功//这里写自定义查询订单表的业务逻辑$isPaySuccess = Order::where([['id',$order_id],['is_pay',1]])->first();//检测订单查询结果if($isPaySuccess){//就是个静态展示页面。view内容就是支付成功/失败的<h1>支付成功</h1>的标签。return redirect()->route('h5.goods.goodsList',$isPaySuccess['students_id'])->with('success','支付成功');// return view('h5.wechatPay.pay_return');//进入支付成功页面//return $this->send(200,true,false,'支付成功');}else{//就是个静态展示页面。view内容就是支付成功/失败的<h1>支付失败</h1>的标签。return redirect()->route('h5.goods.goodsList',$isPaySuccess['students_id'])->with('error','error');}}//获取微信公众号openidpublic function getWechatMpOpenid(Request $request){$code = (string)$request->code;//在微信网页获取到的code,用来换openid$appid = $this->wechatPay['app_id'];//测试账号的appid$secret = $this->wechatPay['app_secret'];//测试账号的app_secret$url = "https://api./sns/oauth2/access_token?appid={$appid}&secret={$secret}&code={$code}&grant_type=authorization_code";//这链接格式是微信官方给的不用改,把参数拼进去就行// 1. 初始化一个cURL会话$ch = curl_init();//设置选项,包括URLcurl_setopt($ch, CURLOPT_URL,$url);curl_setopt($ch, CURLOPT_RETURNTRANSFER, 1);curl_setopt($ch, CURLOPT_HEADER, 0);//执行并获取HTML文档内容$response = curl_exec($ch);// 4. 释放cURL句柄,关闭一个cURL会话curl_close($ch);$response = json_decode($response,true);return ['code'=>200,'data'=>['openid'=>$response['openid'],'array'=>$response]];}}

该处使用的url网络请求的数据。


微信官方后台

1.微信公众平台配置我方项目域名,如下图,若与下图不符,请检查你的公众号是否没有进行认证处理

要是你不想花钱测试支付,可以在侧边栏 开发→开发者工具→公众平台测试账号 中申请测试账号,并进行支付测试,需要注意:你在微信官方给测试账号中支付的花销是退不回来的!!!退不回来的!!!退不回来的!!!

2.微信公众号在侧边栏 微信支付 与商户号进行绑定操作。

3.登录微信商户平台,开通JSAPI支付产品

4.在微信商户平台进行商户号与微信公众号的绑定操作与相关配置。

本内容不代表本网观点和政治立场,如有侵犯你的权益请联系我们处理。
网友评论
网友评论仅供其表达个人看法,并不表明网站立场。