标签:
微信支付API类库来自:https://github.com/zhangv/wechat-pay
请先看一眼官方场景及支付时序图:https://pay.weixin.qq.com/wiki/doc/api/native.php?chapter=6_5
官方API列表:https://pay.weixin.qq.com/wiki/doc/api/native.php?chapter=9_1
二维码生成类库:phpqrcode
走了几天的弯路,直到遇到Lamtin指点(热心网友),他说你既然是集成到CI为何不自己写,我想了想是啊,为什么我一直陷入官方sdk的漩涡里不能跳出来去看这件事,官方提供了API接口,你只需要去调用这些接口啊,post参数啊,是吧,后悔浪费了3天时间。为了不让你们和我一样我把我的思路及代码发布出来,有什么问题可以留言。
纵观微信支付的sdk或者其他的微信支付demo,或多或少的都是围绕官方API接口来写,增加些自己用的方法方便调用之类的,而如果我自己再去写这样的一个东西,第一可能组织不好,基础弱啊,第二可能需要话费大量时间,鉴于此我去寻找比较好用的别人封装的API类库好了,终于不负所望,真有,只可以这个类库几乎没有人用,不过真不错
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
296
297
298
299
300
301
302
303
304
305
306
307
308
309
310
311
312
313
314
315
316
317
318
319
320
321
322
323
324
325
326
327
328
329
330
331
332
333
334
335
336
337
338
339
|
class
WechatPay { const
TRADETYPE_JSAPI = ‘JSAPI‘ ,TRADETYPE_NATIVE =
‘NATIVE‘ ,TRADETYPE_APP =
‘APP‘ ; /** * 错误信息 */ public
$error = null; /** * 错误信息XML */ public
$errorXML = null; /** * 微信支付配置数组 * appid 公众账号appid * mch_id 商户号 * apikey 加密key * appsecret 公众号appsecret * sslcertPath 证书路径(apiclient_cert.pem) * sslkeyPath 密钥路径(apiclient_key.pem) */ private
$_config ; /** * @param $config 微信支付配置数组 */ public
function __construct( $config ) { $this ->_config =
$config ; } /** * JSAPI获取prepay_id * @param $body * @param $out_trade_no * @param $total_fee * @param $notify_url * @param $openid * @return null */ public
function getPrepayId( $body , $out_trade_no , $total_fee , $notify_url , $openid )
{ $data
= array (); $data [ "nonce_str" ] =
$this ->get_nonce_string(); $data [ "body" ] =
$body ; $data [ "out_trade_no" ] =
$out_trade_no ; $data [ "total_fee" ] =
$total_fee ; $data [ "spbill_create_ip" ] =
$_SERVER [ "REMOTE_ADDR" ]; $data [ "notify_url" ] =
$notify_url ; $data [ "trade_type" ] = self::TRADETYPE_JSAPI; $data [ "openid" ] =
$openid ; $result
= $this ->unifiedOrder( $data ); if
( $result [ "return_code" ] ==
"SUCCESS" &&
$result [ "result_code" ] ==
"SUCCESS" ) { return
$result [ "prepay_id" ]; }
else { $this ->error =
$result [ "return_code" ] ==
"SUCCESS" ?
$result [ "err_code_des" ] :
$result [ "return_msg" ]; $this ->errorXML =
$this ->array2xml( $result ); return
null; } } private
function get_nonce_string() { return
substr ( str_shuffle ( "abcdefghijklmnopqrstuvwxyz0123456789" ),0,32); } /** * 统一下单接口 */ public
function unifiedOrder( $params ) { $data
= array (); $data [ "appid" ] =
$this ->_config[ "appid" ]; $data [ "mch_id" ] =
$this ->_config[ "mch_id" ]; $data [ "device_info" ] = (isset( $params [ ‘device_info‘ ])&&trim( $params [ ‘device_info‘ ])!= ‘‘ )? $params [ ‘device_info‘ ]:null; $data [ "nonce_str" ] =
$this ->get_nonce_string(); $data [ "body" ] =
$params [ ‘body‘ ]; $data [ "detail" ] = isset( $params [ ‘detail‘ ])? $params [ ‘detail‘ ]:null; //optional $data [ "attach" ] = isset( $params [ ‘attach‘ ])? $params [ ‘attach‘ ]:null; //optional $data [ "out_trade_no" ] = isset( $params [ ‘out_trade_no‘ ])? $params [ ‘out_trade_no‘ ]:null; $data [ "fee_type" ] = isset( $params [ ‘fee_type‘ ])? $params [ ‘fee_type‘ ]: ‘CNY‘ ; $data [ "total_fee" ] =
$params [ ‘total_fee‘ ]; $data [ "spbill_create_ip" ] =
$params [ ‘spbill_create_ip‘ ]; $data [ "time_start" ] = isset( $params [ ‘time_start‘ ])? $params [ ‘time_start‘ ]:null; //optional $data [ "time_expire" ] = isset( $params [ ‘time_expire‘ ])? $params [ ‘time_expire‘ ]:null; //optional $data [ "goods_tag" ] = isset( $params [ ‘goods_tag‘ ])? $params [ ‘goods_tag‘ ]:null; $data [ "notify_url" ] =
$params [ ‘notify_url‘ ]; $data [ "trade_type" ] =
$params [ ‘trade_type‘ ]; $data [ "product_id" ] = isset( $params [ ‘product_id‘ ])? $params [ ‘product_id‘ ]:null; //required
when trade_type = NATIVE $data [ "openid" ] = isset( $params [ ‘openid‘ ])? $params [ ‘openid‘ ]:null; //required
when trade_type = JSAPI $result
= $this ->post(self::URL_UNIFIEDORDER,
$data ); return
$result ; } private
function post( $url ,
$data , $cert
= false) { $data [ "sign" ] =
$this ->sign( $data ); $xml
= $this ->array2xml( $data ); $ch
= curl_init(); curl_setopt( $ch , CURLOPT_SSL_VERIFYPEER, false); curl_setopt( $ch , CURLOPT_SSL_VERIFYHOST, false); curl_setopt( $ch , CURLOPT_POST, 1); curl_setopt( $ch , CURLOPT_POSTFIELDS,
$xml ); curl_setopt( $ch , CURLOPT_RETURNTRANSFER, true); curl_setopt( $ch , CURLOPT_URL,
$url ); if ( $cert
== true){ //使用证书:cert 与 key 分别属于两个.pem文件 curl_setopt( $ch ,CURLOPT_SSLCERTTYPE, ‘PEM‘ ); curl_setopt( $ch ,CURLOPT_SSLCERT,
$this ->_config[ ‘sslcertPath‘ ]); curl_setopt( $ch ,CURLOPT_SSLKEYTYPE, ‘PEM‘ ); curl_setopt( $ch ,CURLOPT_SSLKEY,
$this ->_config[ ‘sslkeyPath‘ ]); } $content
= curl_exec( $ch ); $array
= $this ->xml2array( $content ); return
$array ; } /** * 数据签名 * @param $data * @return string */ private
function sign( $data ) { ksort( $data ); $string1
= "" ; foreach
( $data
as $k =>
$v ) { if
( $v
&& trim( $v )!= ‘‘ ) { $string1
.= "$k=$v&" ; } } $stringSignTemp
= $string1
. "key=" .
$this ->_config[ "apikey" ]; $sign
= strtoupper (md5( $stringSignTemp )); return
$sign ; } private
function array2xml( $array ) { $xml
= "<xml>"
. PHP_EOL; foreach
( $array
as $k =>
$v ) { if ( $v
&& trim( $v )!= ‘‘ ) $xml
.= "<$k><![CDATA[$v]]></$k>"
. PHP_EOL; } $xml
.= "</xml>" ; return
$xml ; } private
function xml2array( $xml ) { $array
= array (); $tmp
= null; try { $tmp
= ( array ) simplexml_load_string( $xml ); } catch (Exception
$e ){} if ( $tmp
&& is_array ( $tmp )){ foreach
( $tmp
as $k =>
$v ) { $array [ $k ] = (string)
$v ; } } return
$array ; } /** * 扫码支付(模式二)获取支付二维码 * @param $body * @param $out_trade_no * @param $total_fee * @param $notify_url * @param $product_id * @return null */ public
function getCodeUrl( $body , $out_trade_no , $total_fee , $notify_url , $product_id ){ $data
= array (); $data [ "nonce_str" ] =
$this ->get_nonce_string(); $data [ "body" ] =
$body ; $data [ "out_trade_no" ] =
$out_trade_no ; $data [ "total_fee" ] =
$total_fee ; $data [ "spbill_create_ip" ] =
$_SERVER [ "SERVER_ADDR" ]; $data [ "notify_url" ] =
$notify_url ; $data [ "trade_type" ] = self::TRADETYPE_NATIVE; $data [ "product_id" ] =
$product_id ; $result
= $this ->unifiedOrder( $data ); if
( $result [ "return_code" ] ==
"SUCCESS" &&
$result [ "result_code" ] ==
"SUCCESS" ) { return
$result [ "code_url" ]; }
else { $this ->error =
$result [ "return_code" ] ==
"SUCCESS" ?
$result [ "err_code_des" ] :
$result [ "return_msg" ]; return
null; } } /** * 查询订单 * @param $transaction_id * @param $out_trade_no * @return array */ public
function orderQuery( $transaction_id , $out_trade_no ){ $data
= array (); $data [ "appid" ] =
$this ->_config[ "appid" ]; $data [ "mch_id" ] =
$this ->_config[ "mch_id" ]; $data [ "transaction_id" ] =
$transaction_id ; $data [ "out_trade_no" ] =
$out_trade_no ; $data [ "nonce_str" ] =
$this ->get_nonce_string(); $result
= $this ->post(self::URL_ORDERQUERY,
$data ); return
$result ; } /** * 关闭订单 * @param $out_trade_no * @return array */ public
function closeOrder( $out_trade_no ){ $data
= array (); $data [ "appid" ] =
$this ->_config[ "appid" ]; $data [ "mch_id" ] =
$this ->_config[ "mch_id" ]; $data [ "out_trade_no" ] =
$out_trade_no ; $data [ "nonce_str" ] =
$this ->get_nonce_string(); $result
= $this ->post(self::URL_CLOSEORDER,
$data ); return
$result ; } /** * 申请退款 - 使用商户订单号 * @param $out_trade_no 商户订单号 * @param $out_refund_no 退款单号 * @param $total_fee 总金额(单位:分) * @param $refund_fee 退款金额(单位:分) * @param $op_user_id 操作员账号 * @return array */ public
function refund( $out_trade_no , $out_refund_no , $total_fee , $refund_fee , $op_user_id ){ $data
= array (); $data [ "appid" ] =
$this ->_config[ "appid" ]; $data [ "mch_id" ] =
$this ->_config[ "mch_id" ]; $data [ "nonce_str" ] =
$this ->get_nonce_string(); $data [ "out_trade_no" ] =
$out_trade_no ; $data [ "out_refund_no" ] =
$out_refund_no ; $data [ "total_fee" ] =
$total_fee ; $data [ "refund_fee" ] =
$refund_fee ; $data [ "op_user_id" ] =
$op_user_id ; $result
= $this ->post(self::URL_REFUND,
$data ,true); return
$result ; } /** * 申请退款 - 使用微信订单号 * @param $out_trade_no 商户订单号 * @param $out_refund_no 退款单号 * @param $total_fee 总金额(单位:分) * @param $refund_fee 退款金额(单位:分) * @param $op_user_id 操作员账号 * @return array */ public
function refundByTransId( $transaction_id , $out_refund_no , $total_fee , $refund_fee , $op_user_id ){ $data
= array (); $data [ "appid" ] =
$this ->_config[ "appid" ]; $data [ "mch_id" ] =
$this ->_config[ "mch_id" ]; $data [ "nonce_str" ] =
$this ->get_nonce_string(); $data [ "transaction_id" ] =
$transaction_id ; $data [ "out_refund_no" ] =
$out_refund_no ; $data [ "total_fee" ] =
$total_fee ; $data [ "refund_fee" ] =
$refund_fee ; $data [ "op_user_id" ] =
$op_user_id ; $result
= $this ->post(self::URL_REFUND,
$data ,true); return
$result ; } /** * 下载对账单 * @param $bill_date 下载对账单的日期,格式:20140603 * @param $bill_type 类型 * @return array */ public
function downloadBill( $bill_date , $bill_type
= ‘ALL‘ ){ $data
= array (); $data [ "appid" ] =
$this ->_config[ "appid" ]; $data [ "mch_id" ] =
$this ->_config[ "mch_id" ]; $data [ "bill_date" ] =
$bill_date ; $data [ "bill_type" ] =
$bill_type ; $data [ "nonce_str" ] =
$this ->get_nonce_string(); $result
= $this ->post(self::URL_DOWNLOADBILL,
$data ); return
$result ; } /** * 获取js支付使用的第二个参数 */ public
function get_package( $prepay_id ) { $data
= array (); $data [ "appId" ] =
$this ->_config[ "appid" ]; $data [ "timeStamp" ] = time(); $data [ "nonceStr" ] =
$this ->get_nonce_string(); $data [ "package" ] =
"prepay_id=$prepay_id" ; $data [ "signType" ] =
"MD5" ; $data [ "paySign" ] =
$this ->sign( $data ); return
$data ; } /** * 获取发送到通知地址的数据(在通知地址内使用) * @return 结果数组,如果不是微信服务器发送的数据返回null * appid * bank_type * cash_fee * fee_type * is_subscribe * mch_id * nonce_str * openid * out_trade_no 商户订单号 * result_code * return_code * sign * time_end * total_fee 总金额 * trade_type * transaction_id 微信支付订单号 */ public
function get_back_data() { $data
= $this ->xml2array( $xml ); if
( $this ->validate( $data )) { return
$data ; }
else { return
null; } } /** * 验证数据签名 * @param $data 数据数组 * @return 数据校验结果 */ public
function validate( $data ) { if
(!isset( $data [ "sign" ])) { return
false; } $sign
= $data [ "sign" ]; unset( $data [ "sign" ]); return
$this ->sign( $data ) ==
$sign ; } /** * 响应微信支付后台通知 * @param $return_code 返回状态码 SUCCESS/FAIL * @param $return_msg 返回信息 */ public
function response_back( $return_code = "SUCCESS" ,
$return_msg =null) { $data
= array (); $data [ "return_code" ] =
$return_code ; if
( $return_msg ) { $data [ "return_msg" ] =
$return_msg ; } $xml
= $this ->array2xml( $data ); print
$xml ; } } |
一、注意:此类库集成到ci我们要改名WechatPay改为Wechatpay让他符ci类库规范,而且文件名也要改保持统一性
二、把Wechatpay.php放在application\libraries文件夹内,将证书之类的,日志文件之类的放置在和wechatpay.php同级目录下即可,当然可以随便放
三、将微信配置信息,商户号、appid、AppSecret、API key、证书位置等信息放在wxpay_config.php文件中,放在application\config目录中
wxpay_config.php代码
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
|
<?php defined( ‘BASEPATH‘ ) OR
exit ( ‘No direct script access allowed‘ ); /** * Created by PhpStorm. * User: sxq * Date: 2016-04-20 * Time: 16:59 */ $config [ ‘appid‘ ] =
‘你的公众号appid‘ ; $config [ ‘mch_id‘ ] =
‘你的商户号‘ ; $config [ ‘apikey‘ ] =
‘你的APIkey‘ ; $config [ ‘appsecret‘ ] =
"你的AppSecret" ; $config [ ‘sslcertPath‘ ] = APPPATH. ‘libraries/cert/apiclient_cert.pem‘ ; $config [ ‘sslkeyPath‘ ] = APPPATH. ‘libraries/cert/apiclient_key.pem‘ ; |
四、phpqrcode文件,这份文件在微信官方sdk中,使用文件有phpqrcode文件夹和qrcode.php也一同放置在application\libraries文件夹内
五、日志文件log.php,这份文件在微信官方sdk中也一同放置在application\libraries文件夹内
1
2
3
4
5
6
|
require_once
(APPPATH. ‘libraries/log.php‘ ); //初始化日志 $logHandler =
new CLogFileHandler(APPPATH. "logs/" . date ( ‘Y-m-d‘ ). ‘.log‘ ); Log::Init( $logHandler , 15); //我在控制器最顶部加了这个实例化,日志文件放在了application/logs文件夹 //调用方式:log::debug("输出信息");简单记录执行信息方便调试 |
六、配置信息写完后,那么在控制器里调用吧(满满的全是干货)
我们首先按照常规的加载配置信息代码一样去加载微信配置信息,最后再加载三方类库wechatpay.php
1
2
3
4
5
6
7
8
9
|
$this ->load->config( ‘wxpay_config‘ ); $wxconfig [ ‘appid‘ ]= $this ->config->item( ‘appid‘ ); $wxconfig [ ‘mch_id‘ ]= $this ->config->item( ‘mch_id‘ ); $wxconfig [ ‘apikey‘ ]= $this ->config->item( ‘apikey‘ ); $wxconfig [ ‘appsecret‘ ]= $this ->config->item( ‘appsecret‘ ); $wxconfig [ ‘sslcertPath‘ ]= $this ->config->item( ‘sslcertPath‘ ); $wxconfig [ ‘sslkeyPath‘ ]= $this ->config->item( ‘sslkeyPath‘ ); //由于此类库构造函数需要传参,我们初始化类库就传参数给他吧 $this ->load->library( ‘Wechatpay‘ , $wxconfig ); |
这步基础信息配置完毕,接下来我们需要构造统一下单API接口参数
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
|
$param [ ‘body‘ ]= "商品名称(自行看文档具体填什么)" ; $param [ ‘attach‘ ]= "我有个参数要传我就穿了个id过来,这里不要有空格避免出错" ; $param [ ‘detail‘ ]= "我填了商品名称加订单号" ; $param [ ‘out_trade_no‘ ]= "商户订单号" ; $param [ ‘total_fee‘ ]= "金额,记得乘以100,微信支付单位默认分" ; //如$total_fee*100 $param [ "spbill_create_ip" ] = $_SERVER [ ‘REMOTE_ADDR‘ ]; //客户端IP地址 $param [ "time_start" ] =
date ( "YmdHis" ); //请求开始时间 $param [ "time_expire" ] = date ( "YmdHis" ,
time() + 600); //请求超时时间 $param [ "goods_tag" ] = urldecode( $productname ); //商品标签,自行填写 $param [ "notify_url" ] = base_url(). "home/wxnotify" ; //自行定义异步通知url $param [ "trade_type" ] =
"NATIVE" ; //扫码支付模式二 $param [ "product_id" ] =
$order ->productid; //正好有产品id就传了个,看文档说自己定义 //调用统一下单API接口 $result = $this ->wechatpay->unifiedOrder( $param ); //这里可以加日志输出,log::debug(json_encode($result)); //成功(return_code和result_code都为SUCCESS)就会返回含有带支付二维码链接的数据 if
(isset( $result [ "code_url" ]) && ! empty ( $result [ "code_url" ]))
{ /> //二维码图片链接 $data [ ‘wxurl‘ ] =
$result [ "code_url" ]; //这里传递商户订单号到扫码视图,是因为我想做跳转,根据商户号去查询订单是否支付成功,如果成功了就跳转,定时轮询微信服务器(这个谁有好的方法可以分享给我啊,表示感谢啦) $data [ ‘orderno‘ ] =
$out_trade_no ; $this ->load->view( ‘home/pay‘ ,
$data ); } |
pay.php扫码视图页面代码如下:这部分代码来自(https://github.com/Alpha2016/wxpay)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
|
<?php if (isset( $wxurl )&&! empty ( $wxurl )){?> <div
class = "bgcolor" > <div
class = "container" > <div
class = "panel" > <div
class = "panel-heading" > <ol
class = "breadcrumb" > <li><a href= "<?php echo base_url().‘home‘;?>" >首页</a><span
class = ‘divider‘ >></span></li> <li
class = "active active-tab" ><span><?php
echo "二维码支付" ;?></span></li> </ol> </div> <div
class = "panel-body" > <div
class = "page-header" >二维码支付</div> <div
class = "text-danger center-block text-center" > <input type= "hidden"
id= "orderno"
value= "<?php echo $orderno;?>" /> <img alt= "扫码支付"
src= "<?php echo base_url().‘home/qrcode?data=‘.urlencode($wxurl);?>"
style= "width:200px;height:200px;" /> </div> </div> </div> </div> </div> <?php }?> <script> // 每半秒请求一次数据,然后判断,跳转,增加用户友好性 $( function (){ orderno = $( ‘#orderno‘ ).val(); start = self.setInterval( "checkstatus(orderno)" , 500); }); function
checkstatus(order_no){ if (order_no == undefined || order_no ==
‘‘ ){ window.clearInterval(start); } else { $.ajax({ url: "<?php echo base_url().‘home/queryorder‘;?>" , type: ‘POST‘ , dataType: ‘json‘ , data:{orderno:orderno}, success: function (msg){ if (msg.trade_state ==
"SUCCESS" ) { window.clearInterval(start); alert( ‘支付成功‘ ); location.href =
"<?php echo base_url().‘home/myorder‘;?>" ; } } }); } } </script> |
其实核心在二维码链接如何转换成二维码图片和如何定时轮询支付结果
1
|
<?php echo
base_url(). ‘home/qrcode?data=‘ .urlencode( $wxurl );?>这句是调用phpqrcode类库<br>轮询方法代码:<br>该部分在home控制器下 |
1
2
3
4
5
6
7
8
9
10
11
12
13
14
|
function
queryorder() { $this ->load->config( ‘wxpay_config‘ ); $wxconfig [ ‘appid‘ ]= $this ->config->item( ‘appid‘ ); $wxconfig [ ‘mch_id‘ ]= $this ->config->item( ‘mch_id‘ ); $wxconfig [ ‘apikey‘ ]= $this ->config->item( ‘apikey‘ ); $wxconfig [ ‘appsecret‘ ]= $this ->config->item( ‘appsecret‘ ); $wxconfig [ ‘sslcertPath‘ ]= $this ->config->item( ‘sslcertPath‘ ); $wxconfig [ ‘sslkeyPath‘ ]= $this ->config->item( ‘sslkeyPath‘ ); $this ->load->library( ‘Wechatpay‘ , $wxconfig ); $out_trade_no
= $_POST [ ‘orderno‘ ];
//调用查询订单API接口 $array
= $this ->wechatpay->orderQuery( ‘‘ , $out_trade_no ); echo
json_encode( $array ); } |
那么二维码类库调用在这里
1
2
3
4
5
6
|
function
qrcode() { require_once (APPPATH. ‘libraries/phpqrcode/phpqrcode.php‘ ); $url
= urldecode( $_GET [ "data" ]); QRcode::png( $url ); } |
那么二维码生成支付图片完成,支付轮询也完成了,该如何去处理业务逻辑呢?
先说明下,这部分有个弊端,如果客户一直不支付那么他就一直轮询,可以自行设置个有效期,我没有设置。如果在轮询到处理业务逻辑怎么样?可以的,但是也有个问题如果客户直接关掉了,你来不及处理的业务怎么办?所以还要确保不掉单,还需要再微信异步通知url那里处理下业务
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
|
//微信异步通知 function
wxnotify() { //$postStr = file_get_contents("php://input");//因为很多都设置了register_globals禁止,不能用$GLOBALS["HTTP_RAW_POST_DATA‘] //这部分困扰了好久用上面这种一直接受不到数据,或者接受了解析不正确,最终用下面的正常了,有哪位愿意指点的可以告知一二 $xml
= $GLOBALS [ ‘HTTP_RAW_POST_DATA‘ ]; //这个需要开启;always_populate_raw_post_data
= On $this ->load->config( ‘wxpay_config‘ ); $wxconfig [ ‘appid‘ ]= $this ->config->item( ‘appid‘ ); $wxconfig [ ‘mch_id‘ ]= $this ->config->item( ‘mch_id‘ ); $wxconfig [ ‘apikey‘ ]= $this ->config->item( ‘apikey‘ ); $wxconfig [ ‘appsecret‘ ]= $this ->config->item( ‘appsecret‘ ); $wxconfig [ ‘sslcertPath‘ ]= $this ->config->item( ‘sslcertPath‘ ); $wxconfig [ ‘sslkeyPath‘ ]= $this ->config->item( ‘sslkeyPath‘ ); $this ->load->library( ‘Wechatpay‘ , $wxconfig ); libxml_disable_entity_loader(true); $array = json_decode(json_encode(simplexml_load_string( $xml ,
‘SimpleXMLElement‘ , LIBXML_NOCDATA)), true); log::debug( $xml ); log::debug(json_encode( $array )); if ( $array !=null) { $out_trade_no
= $array [ ‘out_trade_no‘ ]; $trade_no
= $array [ ‘transaction_id‘ ]; $data [ ‘orderid‘ ]= $array [ ‘attach‘ ]; $this ->load->model( ‘payorder‘ ); $payinfo
= $this ->payorder->GetPayorder( array ( ‘orderno‘
=> $out_trade_no )); if
(! $payinfo ) { $data [ ‘orderno‘ ] =
$out_trade_no ; $data [ ‘money‘ ] =
$array [ ‘total_fee‘ ]; $data [ ‘tradeno‘ ] =
$trade_no ; $rs = $this ->payorder->AddPayorder( $data ); if ( $rs >0) { //告知微信我成功了 $this ->wechatpay->response_back(); } else { //告知微信我失败了继续发 $this ->wechatpay->response_back( "FAIL" ); } } else { $this ->wechatpay->response_back(); } } } |