微信开发|现金红包接口
发表时间: 2017-09-22 15:57:42 | 浏览次数:
小编的公司之前为了吸引用户前来评论,在网站上增加了“微信现金红包”的功能,下面给大家分享一下教程。现金红包有两种,普通红包和裂变红包,下面教程是普通红包。
1.进入微信商户平台,开通“现金红包”功能;
2.下载API证书,证书包里有4个证书文件,这里PHP开发,用到apiclient_cert.pem和apiclient_key.pem两个证书文件;
3.发红包,首先要有钱,所以需先充值费用;
4.为了防止被盗刷,在微信商户平台可以设置相关的一些规则;
前期工作准备好了,下面进入主题。
WxPayJsApi.php(该类也包含了JSAPI支付和扫码支付):
// +----------------------------------------------------------------------
// | 微信支付统一接口
// | 1.JSAPI支付
// | 2.扫码支付
// +----------------------------------------------------------------------
// | 微信现金红包
// +----------------------------------------------------------------------
// | Copyright (c) 2017 http://www.lrfun.com All rights reserved.
// +----------------------------------------------------------------------
// | Author: lrfun <admin@lrfun.com>
// +----------------------------------------------------------------------
// | Date: 2017-06-12
// +----------------------------------------------------------------------
Class WxPayJsApi{
protected $appid;
protected $mchid;
protected $keys;
function __construct(){
$this->appid = "xxx";
$this->mchid = "xxx";
$this->keys = "xxx";
}
/***
* 微信JSAPI支付
* @data 请求返回数据
* @return
**/
public function jsapi($data){
$data['trade_type'] = 'JSAPI';
$result = $this->unifiedorder($data);
$jsApiData = $this->getJsApiParameters($result);
return $jsApiData;
}
/***
* 微信扫码支付
* @data 请求返回数据
* @return
**/
public function native($data){
$data['trade_type'] = 'NATIVE';
$result = $this->unifiedorder($data);
return $result;
}
/***
* 微信支付统一接口
* @data 请求参数
* @return
**/
private function unifiedorder($data){
$parameters = array();
$parameters['appid'] = $this->appid; //公众账号ID
$parameters['mch_id'] = $this->mchid; //商户号
$parameters['nonce_str'] = $this->getNonceStr(); //随机字符串
$parameters['body'] = $data['body']; //商品描述
$parameters['out_trade_no'] = $this->mchid . date("YmdHis"); //商户订单号
$parameters['total_fee'] = $data['total_fee']; //标价金额(单位:分)
$parameters['spbill_create_ip'] = $_SERVER["REMOTE_ADDR"]; //终端IP
$parameters['notify_url'] = 'http://www.lrfun.com/wxPayCallback.php'; //回调网址
$parameters['trade_type'] = $data['trade_type']; //支付类型:JSAPI,NATIVE,APP等
$parameters['openid'] = $data['openid']; //微信用户的openid(前面有发表过如何获取openid的文章,这里不多说了)
$parameters['time_start'] = date("YmdHis"); //交易起始时间
$parameters['time_expire'] = date("YmdHis", time() + 3600); //交易结束时间
$parameters['attach'] = $data['orderId']; //订单ID,用于支付成功后,更新订单状态
$parameters['sign'] = $this->getSign($parameters); //签名
$queryXml = $this->arrayToXml($parameters);
$url = 'https://api.mch.weixin.qq.com/pay/unifiedorder';
$returnData = $this->httpRequest($url, $queryXml);
$result = $this->xmlToArray($returnData);
return $result;
}
/***
* 微信支付生成签名
* @parameters 签名数据
* @return 签名字符串
**/
public function getSign($parameters){
ksort($parameters);
$parametersUrl = urldecode(http_build_query($parameters)) .'&key='. $this->keys;
$sign = strtoupper(md5($parametersUrl));
return $sign;
}
/***
* 数组转xml
* @arr 数组
* @return xml
**/
private function arrayToXml($arr){
if(!is_array($arr) || count($arr) <= 0){
exit("数组数据异常!");
}
$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;
}
/***
* POST或GET请求
* @url 请求url
* @data POST数据
* @return
**/
private function httpRequest($url, $data = ""){
$curl = curl_init();
curl_setopt($curl, CURLOPT_URL, $url);
curl_setopt($curl, CURLOPT_SSL_VERIFYPEER, FALSE);
curl_setopt($curl, CURLOPT_SSL_VERIFYHOST, FALSE);
if(!empty($data)){ //判断是否为POST请求
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转数组
* @url XML
* @return 数组
**/
private function xmlToArray($xml){
if(!$xml){
echo "xml数据异常!";
exit;
}
libxml_disable_entity_loader(true);
$arr = json_decode(json_encode(simplexml_load_string($xml, 'SimpleXMLElement', LIBXML_NOCDATA)), true);
return $arr;
}
/***
* 获取jsapi支付参数
* @data 请求微信返回的数据
* @return JSON
**/
private function getJsApiParameters($data){
$timeStamp = time();
$jsapi["appId"] = $this->appid;
$jsapi["nonceStr"] = $this->getNonceStr();
$jsapi["timeStamp"] = "$timeStamp";
$jsapi["signType"] = "MD5";
$jsapi["package"] = "prepay_id=".$data["prepay_id"];
$jsapi["paySign"] = $this->getSign($jsapi);
$jsApiParameters = json_encode($jsapi);
return $jsApiParameters;
}
/***
* 支付成功回调函数
**/
public function callback(){
$callbackXml = file_get_contents('php://input');
$data = json_decode(json_encode(simplexml_load_string($callbackXml, 'SimpleXMLElement', LIBXML_NOCDATA)), true);
$callbackSign = $data['sign'];
unset($data['sign']);
$sign = $this->getSign($data);
if($sign == $callbackSign){
//这里更新你的订单状态
//根据$data['attach']获取订单信息,更新订单状态
$returnXml = '<xml><return_code><![CDATA[SUCCESS]]></return_code><return_msg><![CDATA[OK]]></return_msg></xml>';
echo returnXml;
}
}
/***
* 生成随机数
* @length 随机字符串长度(默认32位)
* @return
* */
private function getNonceStr($length = 32) {
$chars = "abcdefghijklmnopqrstuvwxyz0123456789";
$str = "";
for ( $i = 0; $i < $length; $i++ ) {
$str .= substr($chars, mt_rand(0, strlen($chars)-1), 1);
}
return $str;
}
/***
* 微信发送现金红包
* @data 请求参数
* @return
**/
public function sendRedPack($data){
$parameters = array();
$parameters['wxappid'] = $this->appid; //公众账号appid
$parameters['mch_id'] = $this->mchid; //商户号
$parameters['nonce_str'] = $this->getNonceStr(); //随机字符串
$parameters['mch_billno'] = $this->getNonceStr(28); //商户订单号
$parameters['send_name'] = "LiuR_Fun"; //商户名称
$parameters['client_ip'] = $_SERVER["REMOTE_ADDR"]; //Ip地址
$parameters['re_openid'] = $data['re_openid']; //用户openid
$parameters['total_amount'] = 100; //付款金额(单位:分;金额范围:1.00~200.00之间)
$parameters['total_num'] = 1; //红包发放总人数
$parameters['wishing'] = "感谢您的评价,祝您生活愉快!"; //红包祝福语
$parameters['act_name'] = "评价赢红包"; //活动名称
$parameters['remark'] = "好评越多得越多,快来抢!"; //备注
$parameters['sign'] = $this->getSign($parameters); //签名
$queryXml = $this->arrayToXml($parameters);
$url = 'https://api.mch.weixin.qq.com/mmpaymkttransfers/sendredpack';
$returnData = $this->curl_post_ssl($url, $queryXml);
$result = $this->xmlToArray($returnData);
return $result;
}
/***
* HTTP请求(带证书)
* @url 请求url
* @vars 请求数据
* @second 超时时间
* @aHeader 请求头部参数
* @return
* */
private function curl_post_ssl($url, $vars, $second=30,$aHeader=array()){
$curl = curl_init();
//超时时间
curl_setopt($curl, CURLOPT_TIMEOUT, $second);
curl_setopt($curl, CURLOPT_RETURNTRANSFER, 1);
//这里设置代理,如果有的话
//curl_setopt($curl, CURLOPT_PROXY, '10.206.30.98');
//curl_setopt($curl, CURLOPT_PROXYPORT, 8080);
curl_setopt($curl, CURLOPT_URL, $url);
curl_setopt($curl, CURLOPT_SSL_VERIFYPEER, false);
curl_setopt($curl, CURLOPT_SSL_VERIFYHOST, false);
//以下两种方式需选择一种
//第一种方法,cert 与 key 分别属于两个.pem文件
//默认格式为PEM,可以注释
curl_setopt($curl, CURLOPT_SSLCERTTYPE, 'PEM');
curl_setopt($curl, CURLOPT_SSLCERT, getcwd().'/apiclient_cert.pem');
//默认格式为PEM,可以注释
curl_setopt($curl, CURLOPT_SSLKEYTYPE, 'PEM');
curl_setopt($curl, CURLOPT_SSLKEY ,getcwd().'/apiclient_key.pem');
//第二种方式,两个文件合成一个.pem文件
//curl_setopt($curl,CURLOPT_SSLCERT,getcwd().'/all.pem');
if( count($aHeader) >= 1 ){
curl_setopt($curl, CURLOPT_HTTPHEADER, $aHeader);
}
curl_setopt($curl, CURLOPT_POST, 1);
curl_setopt($curl, CURLOPT_POSTFIELDS, $vars);
$data = curl_exec($curl);
if($data){
curl_close($curl);
return $data;
} else {
$error = curl_errno($curl);
echo "call faild, errorCode:$error\n";
curl_close($curl);
return false;
}
}
}
调用代码sendRedPack.php:
header("Content-type: text/html; charset=utf-8");
require_once('WxPayJsApi.php');
$wxPayJsApi = new WxPayJsApi();
$data = array("re_openid" => "oSKzJvk9U8R8WmVo7ylk3b-frjuo");
$result = $wxPayJsApi->sendRedPack($data);
if($result['result_code'] == "SUCCESS"){
echo "现金红包发送成功!";
}
上一篇:微信公众平台|模板消息群发功能
下一篇:PHP 微信公众号的基本配置token验证失败