Home WeChat Applet WeChat Development Detailed explanation of Thinkphp integrating WeChat payment function

Detailed explanation of Thinkphp integrating WeChat payment function

Dec 02, 2017 am 10:21 AM
php thinkphp Detailed explanation

WeChat payment is now common in our lives, and WeChat applets are also very popular during development. In this article, we will continue to explain to you about Thinkphp’s integration of WeChat payment functions.

1. WeChat public account:

Set the domain name that can obtain user ID information permissions among the unique appid, appscrect, and interface permissions (each user will have a unique ID for different publics. Obtain the basic information of the user's WeChat account through this ID (see the WeChat developer documentation for details), set the WeChat payment authorization directory on the WeChat payment button (written to the level of the controller that initiates the request), and set the developer's WeChat account as a test whitelist (Required when using WeChat developer tools)

2. WeChat payment platform:

Merchant platform login account, payment key (you can set it yourself at any time, there can only be one),

3. Integrate the logic into thinkphp:

Set the front-end WeChat payment button and click to call the payment initiation controller method,

The controller runs, references the WeChat payment class, and obtains the user openid , obtain the order data, splice out all the data required by ordinary merchants' prepayment jsp, display the customized payment page,

Click to pay on the payment page, and call the jspi script function provided by WeChat to initiate payment to initiate payment. ,

After the payment is completed, the page will redirect to (the jump directory {:U('controller/function)} set in the script function of the custom payment page), and the asynchronous (silent) setting will be Processing order logic (recording payment time, marking as paid, marking as WeChat payment), etc.

Code:

WeChat payment button on my order page:

WeChat Payment

Initiate payment controller Wxpay:

<?php
namespace Home\Controller;
use Think\Controller;
//微信支付类
class WxpayController extends Controller {
 //获取access_token过程中的跳转uri,通过跳转将code传入jsapi支付页面
 public function js_api_start(){
  if(!empty($_GET[&#39;order_key_num&#39;])){
   // session(array(&#39;pay_now_id&#39;=>$_GET[&#39;order_key_num&#39;],&#39;expire&#39;=>3600));
   S(&#39;pay_now_id&#39;,$_GET[&#39;order_key_num&#39;],3600);
  }
  vendor(&#39;Weixinpay.WxPayPubHelper&#39;);
  //使用jsapi接口
  $jsApi = new \JsApi_pub();
  //=========步骤1:网页授权获取用户openid============
  //通过code获得openid
   if($_GET[&#39;code&#39;] == &#39;&#39;){
   //跳转
    $redirect_uri = &#39;https://当前域名+模块+控制器+方法&#39;;
    $url = &#39;https://open.weixin.qq.com/connect/oauth2/authorize
    ?appid=公众号特有IDredirect_uri=&#39;.$redirect_uri.&#39;&response_type=code&scope=snsapi_base&state=STATE#wechat_redirect&#39;;
    header("Location: $url");
    exit();
   }else{
   //获取openid
   $url = &#39;https://api.weixin.qq.com/sns/oauth2/access_token
   ?appid=公众号ID&secret=公众号scrept&code=&#39;.$_GET[&#39;code&#39;].&#39;&grant_type=authorization_code&#39;; 
   $openid_arr = json_decode(file_get_contents($url),true);
  }
  $openid=$openid_arr[&#39;openid&#39;];
  $pay_now_id = S(&#39;pay_now_id&#39;);
  if($pay_now_id){
   $id=$pay_now_id;
   $o = D(&#39;order_info&#39;);
   $order_info = $o->where(&#39;order_id = %d&#39;,$id)->find();
   if(empty($order_info[&#39;paycode&#39;])){
    $order_info[&#39;paycode&#39;] = &#39;weixin&#39;;
   }
   if($order_info[&#39;is_pay&#39;]){
    $this->error(&#39;当前订单已经支付&#39;);
   }
  }else{
   $this->error("不存在当前订单编号!");
  }
   $res = array(
   &#39;order_sn&#39; => $order_info[&#39;order_sn&#39;],
   &#39;order_amount&#39; => $order_info[&#39;pay_money&#39;]
   );
  //=========步骤2:使用统一支付接口,获取prepay_id============
  //使用统一支付接口
  $unifiedOrder = new \UnifiedOrder_pub();
  //设置统一支付接口参数
  //设置必填参数
  //appid已填,商户无需重复填写
  //mch_id已填,商户无需重复填写
  //noncestr已填,商户无需重复填写
  //spbill_create_ip已填,商户无需重复填写
  //sign已填,商户无需重复填写
  $total_fee = $order_info[&#39;pay_money&#39;]*100;
  // $total_fee = $res[&#39;order_amount&#39;];
  //$total_fee = 1;
  // var_dump($order_info[&#39;pay_money&#39;]);die;
  $body = "订单支付";
  $unifiedOrder->setParameter("openid", "$openid");//用户标识
  $unifiedOrder->setParameter("body", &#39;商品采购&#39;);//商品描述
  //自定义订单号,此处仅作举例
  $unifiedOrder->setParameter("out_trade_no", $order_info[&#39;order_sn&#39;]);//商户订单号 
  $unifiedOrder->setParameter("total_fee", $total_fee);//总金额
  //$unifiedOrder->setParameter("attach", "order_sn={$res[&#39;order_sn&#39;]}");//附加数据 
  $unifiedOrder->setParameter("notify_url", \WxPayConf_pub::NOTIFY_URL);//通知地址 
  $unifiedOrder->setParameter("trade_type", "JSAPI");//交易类型
  //非必填参数,商户可根据实际情况选填
  //$unifiedOrder->setParameter("sub_mch_id","XXXX");//子商户号 
  //$unifiedOrder->setParameter("device_info","XXXX");//设备号 
  //$unifiedOrder->setParameter("attach","XXXX");//附加数据 
  //$unifiedOrder->setParameter("time_start","XXXX");//交易起始时间
  //$unifiedOrder->setParameter("time_expire","XXXX");//交易结束时间 
  //$unifiedOrder->setParameter("goods_tag","XXXX");//商品标记 
  //$unifiedOrder->setParameter("openid","XXXX");//用户标识
  //$unifiedOrder->setParameter("product_id","XXXX");//商品ID
  $prepay_id = $unifiedOrder->getPrepayId();
  // var_dump($prepay_id);die;
  //=========步骤3:使用jsapi调起支付============
  $jsApi->setPrepayId($prepay_id);
  $jsApiParameters = $jsApi->getParameters();
  $wxconf = json_decode($jsApiParameters, true);
  if ($wxconf[&#39;package&#39;] == &#39;prepay_id=&#39;) {
   $this->error(&#39;当前订单存在异常!&#39;);
  }
  $this->assign(&#39;res&#39;, $res);
  $this->assign(&#39;jsApiParameters&#39;, $jsApiParameters);
  $this->display(&#39;jsapi&#39;);
 }
 //异步通知url,商户根据实际开发过程设定
 public function notify_url() {
  vendor(&#39;Weixinpay.WxPayPubHelper&#39;);
  //使用通用通知接口
  $notify = new \Notify_pub();
  //存储微信的回调
  $xml = $GLOBALS[&#39;HTTP_RAW_POST_DATA&#39;]; 
  $notify->saveData($xml);
  //验证签名,并回应微信。
  //对后台通知交互时,如果微信收到商户的应答不是成功或超时,微信认为通知失败,
  //微信会通过一定的策略(如30分钟共8次)定期重新发起通知,
  //尽可能提高通知的成功率,但微信不保证通知最终能成功。
  if($notify->checkSign() == FALSE){
   $notify->setReturnParameter("return_code", "FAIL");//返回状态码
   $notify->setReturnParameter("return_msg", "签名失败");//返回信息
  }else{
   $notify->setReturnParameter("return_code", "SUCCESS");//设置返回码
  }
  $returnXml = $notify->returnXml();
  //==商户根据实际情况设置相应的处理流程,此处仅作举例=======
  //以log文件形式记录回调信息
  //$log_name = "notify_url.log";//log文件路径
  //$this->log_result($log_name, "【接收到的notify通知】:\n".$xml."\n");
  $parameter = $notify->xmlToArray($xml);
  //$this->log_result($log_name, "【接收到的notify通知】:\n".$parameter."\n");
  if($notify->checkSign() == TRUE){
   if ($notify->data["return_code"] == "FAIL") {
    //此处应该更新一下订单状态,商户自行增删操作
    //$this->log_result($log_name, "【通信出错】:\n".$xml."\n");
    //更新订单数据【通信出错】设为无效订单
    echo &#39;error&#39;;
   }
   else if($notify->data["result_code"] == "FAIL"){
    //此处应该更新一下订单状态,商户自行增删操作
    //$this->log_result($log_name, "【业务出错】:\n".$xml."\n");
    //更新订单数据【通信出错】设为无效订单
    echo &#39;error&#39;;
   }
   else{
    //$this->log_result($log_name, "【支付成功】:\n".$xml."\n");
    //我这里用到一个process方法,成功返回数据后处理,返回地数据具体可以参考微信的文档
    if ($this->process($parameter)) {
     //处理成功后输出success,微信就不会再下发请求了
     echo &#39;success&#39;;
    }else {
     //没有处理成功,微信会间隔的发送请求
     echo &#39;error&#39;;
    }
   }
  }
 }
 //订单处理
 private function process($parameter) {
  //此处应该更新一下订单状态,商户自行增删操作
  /*
  * 返回的数据最少有以下几个
  * $parameter = array(
   &#39;out_trade_no&#39; => xxx,//商户订单号
   &#39;total_fee&#39; => XXXX,//支付金额
   &#39;openid&#39; => XXxxx,//付款的用户ID
  );
  */
  $data = array(
      &#39;order_sn&#39;=>$parameter[&#39;out_trade_no&#39;],
      &#39;des&#39;=>(&#39;订单交易:&#39;.$parameter[&#39;out_trade_no&#39;]),
      &#39;money&#39;=>$parameter[&#39;total_fee&#39;],
     );
  orderhandlestarysdgdss($data);//这是一个common方法,他会将该订单状态设置为已支付之类的
  return true;
 }
}
?>
Copy after login

After initiating payment, splice the prepayment data parameters (see the WeChat ordinary merchant developer documentation for the parameter list - WeChat Payment - Unified Order) display page:

<!DOCTYPE html>
<html>
<head>
<meta http-equiv="Content-Type" content="text/html; charset=UTF-8">
<meta http-equiv="X-UA-Compatible" content="IE=edge">
<meta content="width=device-width, initial-scale=1.0, maximum-scale=1.0, user-scalable=0;" name="viewport" />
<meta name="format-detection" content="telephone=no"/> 
<title>下</title>
<meta http-equiv="Content-Security-Policy" content="upgrade-insecure-requests">
<meta name="keyword" content="">
<meta name="description" content="">
<script type="text/javascript">
var order_sn = "{$res[&#39;order_sn&#39;]}";
//调用微信JS api 支付
function jsApiCall(){
 WeixinJSBridge.invoke(
  &#39;getBrandWCPayRequest&#39;,
  <?php echo $jsApiParameters; ?>,
  function(res){
   //如果支付成功
   if (res.err_msg == &#39;get_brand_wcpay_request:ok&#39;) {
    //支付成功后跳转的地址
    location.href = "{:U(&#39;Home/User/my_order&#39;)}";
   }else if (res.err_msg == &#39;get_brand_wcpay_request:cancel&#39;) {
    alert(&#39;请尽快完成支付哦!&#39;);
   }else if (res.err_msg == &#39;get_brand_wcpay_request:fail&#39;) {
    alert(&#39;支付失败&#39;);
   }else {
    alert(&#39;意外错误&#39;);
   }
   //WeixinJSBridge.log(res.err_msg);
   //alert(res.err_code+res.err_desc+res.err_msg);
   /*if (res.err_msg == &#39;get_brand_wcpay_request:ok&#39;) {
    alert(&#39;支付成功&#39;);
   }else {
    alert(&#39;取消支付&#39;);
   }*/
  }
 );
}
function callpay(){
 if (typeof WeixinJSBridge == "undefined"){
  if( document.addEventListener ){
   document.addEventListener(&#39;WeixinJSBridgeReady&#39;, jsApiCall, false);
  }else if (document.attachEvent){
   document.attachEvent(&#39;WeixinJSBridgeReady&#39;, jsApiCall); 
   document.attachEvent(&#39;onWeixinJSBridgeReady&#39;, jsApiCall);
  }
 }else{
  jsApiCall();
 }
}
</script>
<style>
*{font-family:&#39;微软雅黑&#39;,&#39;Microsoft YaHei&#39;;}
body #head{position:relative;z-index:99999999999999;padding:0 10px;}
body .zh-head{padding:0 0 0 0;height:auto;}
.zh-head-conter{position:relative;height:40px;}
.zh-logo{position:absolute;left:50%;top:0;margin:0 0 0 -60px;float:none;width:auto;}
.zh-logo a{display:block;}
.zh-logo img{width:120px;height:40px;display:block;}
.heads_fix .zh-logo{}
#head{position:fixed!important;left:0;top:0;right:0;z-index:99999;background:#fff;border-bottom:1px solid #ddd;}
.zh-logo{height:40px;}
.flowpay{margin-top:25%;}
.flowpay dt{text-align:center;}
.flowpay strong.price{font-size:40px;}
.wxLogo{text-align:center;}
.wxLogo img{}
.flowpay dd{margin:0;padding:20px 0 10px 0;}
.flowpay dd input{margin:0 auto;padding:0;width:90%;height:45px;line-height:45px;border:0;border-radius:4px;background:#0CBC0A;color:#fff;font-size:17px;display:block;-webkit-appearance:none;-moz-appearance:none;appearance:none;outline:none;}
</style>
</head>
<body>
<!--头部开始-->
<div class="flowpay">
 <dl>
  <dt>
   <p class="wxLogo"><img src="/static/imghw/default1.png"  data-src="__PUBLIC__/home/images/1479953699138120.png"  class="lazy"   alt=""></p>
   本次订单需支付:¥<strong class="price">{$res[&#39;order_amount&#39;]}</strong> 元
  </dt>
  <dd>
   <input type="button" id="hhhhhh" onclick="callpay()" value="立即支付" />
  </dd>
 </dl>
</div>
<!--尾结束-->
</body>
</html>
Copy after login

Then there is the class file:

Detailed explanation of Thinkphp integrating WeChat payment function

The cacert is the certificate storage directory; the certificate is not necessarily required;

## Just look for the #vendor folder in My Files.

The above content is about Thinkphp integrating WeChat payment function, I hope it can help everyone.

Related recommendations:

How to implement WeChat applet payment and refund in php

Introduction example of WeChat applet development

Encapsulation of network requests by WeChat applet

Example of password input by WeChat applet

WeChat applet Robot automatic customer service function

The above is the detailed content of Detailed explanation of Thinkphp integrating WeChat payment function. For more information, please follow other related articles on the PHP Chinese website!

Statement of this Website
The content of this article is voluntarily contributed by netizens, and the copyright belongs to the original author. This site does not assume corresponding legal responsibility. If you find any content suspected of plagiarism or infringement, please contact admin@php.cn

Hot AI Tools

Undresser.AI Undress

Undresser.AI Undress

AI-powered app for creating realistic nude photos

AI Clothes Remover

AI Clothes Remover

Online AI tool for removing clothes from photos.

Undress AI Tool

Undress AI Tool

Undress images for free

Clothoff.io

Clothoff.io

AI clothes remover

Video Face Swap

Video Face Swap

Swap faces in any video effortlessly with our completely free AI face swap tool!

Hot Tools

Notepad++7.3.1

Notepad++7.3.1

Easy-to-use and free code editor

SublimeText3 Chinese version

SublimeText3 Chinese version

Chinese version, very easy to use

Zend Studio 13.0.1

Zend Studio 13.0.1

Powerful PHP integrated development environment

Dreamweaver CS6

Dreamweaver CS6

Visual web development tools

SublimeText3 Mac version

SublimeText3 Mac version

God-level code editing software (SublimeText3)

PHP 8.4 Installation and Upgrade guide for Ubuntu and Debian PHP 8.4 Installation and Upgrade guide for Ubuntu and Debian Dec 24, 2024 pm 04:42 PM

PHP 8.4 brings several new features, security improvements, and performance improvements with healthy amounts of feature deprecations and removals. This guide explains how to install PHP 8.4 or upgrade to PHP 8.4 on Ubuntu, Debian, or their derivati

How To Set Up Visual Studio Code (VS Code) for PHP Development How To Set Up Visual Studio Code (VS Code) for PHP Development Dec 20, 2024 am 11:31 AM

Visual Studio Code, also known as VS Code, is a free source code editor — or integrated development environment (IDE) — available for all major operating systems. With a large collection of extensions for many programming languages, VS Code can be c

Explain JSON Web Tokens (JWT) and their use case in PHP APIs. Explain JSON Web Tokens (JWT) and their use case in PHP APIs. Apr 05, 2025 am 12:04 AM

JWT is an open standard based on JSON, used to securely transmit information between parties, mainly for identity authentication and information exchange. 1. JWT consists of three parts: Header, Payload and Signature. 2. The working principle of JWT includes three steps: generating JWT, verifying JWT and parsing Payload. 3. When using JWT for authentication in PHP, JWT can be generated and verified, and user role and permission information can be included in advanced usage. 4. Common errors include signature verification failure, token expiration, and payload oversized. Debugging skills include using debugging tools and logging. 5. Performance optimization and best practices include using appropriate signature algorithms, setting validity periods reasonably,

PHP Program to Count Vowels in a String PHP Program to Count Vowels in a String Feb 07, 2025 pm 12:12 PM

A string is a sequence of characters, including letters, numbers, and symbols. This tutorial will learn how to calculate the number of vowels in a given string in PHP using different methods. The vowels in English are a, e, i, o, u, and they can be uppercase or lowercase. What is a vowel? Vowels are alphabetic characters that represent a specific pronunciation. There are five vowels in English, including uppercase and lowercase: a, e, i, o, u Example 1 Input: String = "Tutorialspoint" Output: 6 explain The vowels in the string "Tutorialspoint" are u, o, i, a, o, i. There are 6 yuan in total

How do you parse and process HTML/XML in PHP? How do you parse and process HTML/XML in PHP? Feb 07, 2025 am 11:57 AM

This tutorial demonstrates how to efficiently process XML documents using PHP. XML (eXtensible Markup Language) is a versatile text-based markup language designed for both human readability and machine parsing. It's commonly used for data storage an

Explain late static binding in PHP (static::). Explain late static binding in PHP (static::). Apr 03, 2025 am 12:04 AM

Static binding (static::) implements late static binding (LSB) in PHP, allowing calling classes to be referenced in static contexts rather than defining classes. 1) The parsing process is performed at runtime, 2) Look up the call class in the inheritance relationship, 3) It may bring performance overhead.

What are PHP magic methods (__construct, __destruct, __call, __get, __set, etc.) and provide use cases? What are PHP magic methods (__construct, __destruct, __call, __get, __set, etc.) and provide use cases? Apr 03, 2025 am 12:03 AM

What are the magic methods of PHP? PHP's magic methods include: 1.\_\_construct, used to initialize objects; 2.\_\_destruct, used to clean up resources; 3.\_\_call, handle non-existent method calls; 4.\_\_get, implement dynamic attribute access; 5.\_\_set, implement dynamic attribute settings. These methods are automatically called in certain situations, improving code flexibility and efficiency.

PHP and Python: Comparing Two Popular Programming Languages PHP and Python: Comparing Two Popular Programming Languages Apr 14, 2025 am 12:13 AM

PHP and Python each have their own advantages, and choose according to project requirements. 1.PHP is suitable for web development, especially for rapid development and maintenance of websites. 2. Python is suitable for data science, machine learning and artificial intelligence, with concise syntax and suitable for beginners.

See all articles