PHP接口微信支付
PHP后台调用微信支付下单
function wx_getPayRequest($openid, $orderid, $rmb, $title,$appoids)
{
$nonce = $orderid.mt_rand(10000,99999);
$orderid=$orderid.'_'.$nonce;//str_replace(",","_",$appoids);
//Log::write('\n ================'.$orderid,'notice');
$srct='0x'.md5(config('app.environment')['paykey'].$orderid);
$notify = '';//回调地址,自己写,支付成功回调,在回调页面进行更改与用户金钱相关的代码
$url= 'https://api.mch.weixin.qq.com/pay/unifiedorder';//统一接口prepay_id
// post data
$now = time().'';//时间
$appid ='';//小程序ID 写到一个类里面了 方便后期修改 当然也可以在这里直接写
$mchid ='';//商户号
// Log::write('\n $mchid================'.json_encode($mchid),'notice');
// Log::write('\n $appid================'.json_encode($appid),'notice');
$data = array(
'appid' => $appid,
'mch_id' => $mchid,
'spbill_create_ip' => '127.0.0.1',//终端ip Y
'nonce_str' => $nonce, //随机字符串Y
'openid' => $openid, //用户标识 N
'body' => $title, //商品描述 Y
// 'detail' => $body, //商品详情 N
'attach' => $appoids, //附加数据 N
'out_trade_no' => $orderid, //商户订单号 Y
'total_fee' => $rmb, //总金额 单位分 int Y
'notify_url' => $notify, //通知地址 Y
'trade_type' => 'JSAPI',
);
$data[ 'sign' ] = self::MakeSign($data);
//echo $data[ 'sign' ];
// Log::write('\n sign================'.json_encode($data[ 'sign' ]),'notice');
$xml=self::wx_toXML($data);
$ret = $this->http_request($url,$xml);
$json = self::wx_parseXML( $ret );
//Log::write('\n ================'.json_encode($json),'notice');
if( !$json || !isset($json[ 'prepay_id' ]) )
{
return array( 'payCode'=>1,'ret' => 'fail', 'tip' => $json[ 'return_msg' ] );
}
$prepayid = $json[ 'prepay_id' ];
$req = array(
'appId' => $appid,
'timeStamp' => $now,
'nonceStr' => $nonce,
'package' => 'prepay_id='.$prepayid,
'signType' => 'MD5',
);
$req[ 'paySign' ] = self::wx_getPkgSign($req);
//$req[ 'notify' ] = $notify;
return $req;
}
///作用:格式化参数,签名过程需要使用
private function formatBizQueryParaMap($paraMap, $urlencode) {
$buff = "";
ksort($paraMap);
foreach ($paraMap as $k => $v) {
if ($urlencode) {
$v = urlencode($v);
}
$buff .= $k . "=" . $v . "&";
}
$reqPar;
if (strlen($buff) > 0) {
$reqPar = substr($buff, 0, strlen($buff) - 1);
}
return $reqPar;
}
public function wx_getPkgSign($req )
{
foreach ($req as $k => $v) {
$Parameters[$k] = $v;
}
//签名步骤一:按字典序排序参数
ksort($Parameters);
$String = $this->formatBizQueryParaMap($Parameters, false);
//签名步骤二:在string后加入KEY
$String = $String . "&key=" . config('app.environment')['paykey'];
//签名步骤三:MD5加密
$String = md5($String);
//签名步骤四:所有字符转为大写
$result_ = strtoupper($String);
return $result_;
}
public function wx_toXML( $data )
{
$xml = '<xml>';
foreach( $data as $key => $val )
{
$xml .= '<' . $key . '><![CDATA[' . $val . ']]></' . $key . '>';
}
$xml .= '</xml>';
return $xml;
}
/**
* 输出xml字符
* @param $data
* @return string
*/
public function ToXml($data)
{
if(!is_array($data)
|| count($data) <= 0)
{
throw new WxPayException("数组数据异常!");
}
$xml = "<xml>";
foreach ($data as $key=>$val)
{
if (is_numeric($val)){
$xml.="<".$key.">".$val."</".$key.">";
}else{
$xml.="<".$key."><![CDATA[".$val."]]></".$key.">";
}
}
$xml.="</xml>";
return $xml;
}
/**
* 格式化参数格式化成url参数
*/
public function ToUrlParams($data)
{
$buff = "";
foreach ($data as $k => $v)
{
if($k != "sign" && $v != "" && !is_array($v)){
$buff .= $k . "=" . $v . "&";
}
}
$buff = trim($buff, "&");
return $buff;
}
/**
* 生成签名
* @param $data
* @return string 签名,本函数不覆盖sign成员变量,如要设置签名需要调用SetSign方法赋值
*/
public function MakeSign($data)
{
//签名步骤一:按字典序排序参数
ksort($data);
$string = $this->ToUrlParams($data);
//签名步骤二:在string后加入KEY
$string = $string . "&key=".config('app.environment')['paykey'];
//签名步骤三:MD5加密
$string = md5($string);
//签名步骤四:所有字符转为大写
$result = strtoupper($string);
return $result;
}
public function wx_parseXML( $str )
{
$rsp = array();
$xml = @simplexml_load_string( $str );
if( $xml && $xml->children() )
{
foreach( $xml->children() as $node )
{
if( $node->children() )
{
$k = $node->getName();
$nodeXml = $node->asXML();
$v = substr( $nodeXml, strlen($k)+2, strlen($nodeXml)-2*strlen($k)-5 );
}
else
{
$k = $node->getName();
$v = (string)$node;
}
$rsp[ $k ] = $v;
}
}
return $rsp;
}
public function payRefund($wxtranid,$order_childid, $ordertotalrmb,$refundrmb){
$appid = config('environment')[config('current_environment')]['appid'];//小程序ID 写到一个类里面了 方便后期修改 当然也可以在这里直接写
$mchid = config('environment')[config('current_environment')]['mchid'];//商户号
$nonce = $order_childid.mt_rand(10000,99999);
Log::write('取消预约单申请退款中===$ordertotalrmb='.$ordertotalrmb.'=======$refundrmb='.$refundrmb,'notice');
//统一下单退款参数构造
$unifiedorder = array(
'appid' => $appid,
'mch_id' => $mchid,
'nonce_str' => $nonce,
'transaction_id' => $wxtranid,
'out_refund_no' => $order_childid,
'total_fee' => intval($ordertotalrmb),
'refund_fee' => intval($refundrmb),
'notify_url'=>'https://wxcon.drmpsy.com.cn/api/appo/payBackSuccess'
);
$unifiedorder['sign'] = self::wx_getPkgSign($unifiedorder);
Log::write('$content111111================'.json_encode($unifiedorder),'notice');
//请求数据
$xmldata = self::wx_toXml($unifiedorder);
$opUrl = "https://api.mch.weixin.qq.com/secapi/pay/refund";
//$res = $this->http_request($opUrl, $xmldata);
$res = $this->postXmlSSLCurl($xmldata,$opUrl);
Log::write($res,'notice');
if (!$res) {
return "Can't connect the server";
}
$content = self::xmlToArray($res);
Log::write('$content================'.json_encode($content),'notice');
try{
if (strval($content['result_code']) == 'FAIL') {
return strval($content['err_code_des']);
}
}
catch (Exception $err){
}
try{
if ($content['return_code']&&strval($content['return_code']) == 'FAIL') {
return strval($content['return_msg']);
}
}
catch (Exception $err){
}
return $content;
}
public function xmlToArray($xml){
$array_data = json_decode(json_encode(simplexml_load_string($xml, 'SimpleXMLElement', LIBXML_NOCDATA)), true);
return $array_data;
}
//需要使用证书的请求
private function postXmlSSLCurl($xml,$url,$second=30)
{
$ch = curl_init();
//超时时间
curl_setopt($ch,CURLOPT_TIMEOUT,$second);
//这里设置代理,如果有的话
//curl_setopt($ch,CURLOPT_PROXY, '8.8.8.8');
//curl_setopt($ch,CURLOPT_PROXYPORT, 8080);
curl_setopt($ch,CURLOPT_URL, $url);
curl_setopt($ch,CURLOPT_SSL_VERIFYPEER,FALSE);
curl_setopt($ch,CURLOPT_SSL_VERIFYHOST,FALSE);
//设置header
curl_setopt($ch,CURLOPT_HEADER,FALSE);
//要求结果为字符串且输出到屏幕上
curl_setopt($ch,CURLOPT_RETURNTRANSFER,TRUE);
//设置证书
//使用证书:cert 与 key 分别属于两个.pem文件
//默认格式为PEM,可以注释
curl_setopt($ch,CURLOPT_SSLCERTTYPE,'PEM');
curl_setopt($ch,CURLOPT_SSLCERT, '/nfs/website/wx.drmpsy.com.cn/api/cert/apiclient_cert.pem');
//默认格式为PEM,可以注释
curl_setopt($ch,CURLOPT_SSLKEYTYPE,'PEM');
curl_setopt($ch,CURLOPT_SSLKEY,'/nfs/website/wx.drmpsy.com.cn/api/cert/apiclient_key.pem');
//post提交方式
curl_setopt($ch,CURLOPT_POST, true);
curl_setopt($ch,CURLOPT_POSTFIELDS,$xml);
$data = curl_exec($ch);
//返回结果
if($data){
curl_close($ch);
return $data;
}
else {
$error = curl_errno($ch);
echo "curl出错,错误码:$error"."<br>";
curl_close($ch);
return false;
}
}
//curl请求
public 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;
}
PHP接口微信支付的更多相关文章
- 官方微信接口(全接口) - 微信摇一摇接口/微信多客服接口/微信支付接口/微信红包接口/微信卡券接口/微信小店接口/JSAPI
微信入口绑定,微信事件处理,微信API全部操作包含在这些文件中.微信支付.微信红包.微信卡券.微信小店. 微信开发探讨群 330393916 <?php /** * Description o ...
- (实用篇)php官方微信接口大全(微信支付、微信红包、微信摇一摇、微信小店)
微信入口绑定,微信事件处理,微信API全部操作包含在这些文件中.内容有:微信摇一摇接口/微信多客服接口/微信支付接口/微信红包接口/微信卡券接口/微信小店接口/JSAPI <?php class ...
- JAVA微信支付接口开发——支付
微信支付接口开发--支付 这几天在做支付服务,系统接入了支付宝.微信.银联三方支付接口.个人感觉支付宝的接口开发较为简单,并且易于测试. 关于数据传输,微信是用xml,所以需要对xml进行解析. 1. ...
- 微信支付开发+{ping++}微信支付托管
------------------------微信支付接口------------------------------- 微信支付开发并没有想象中的那么难,主要是微信提供了sdk. 微信公众号必须是 ...
- Spring Boot中的微信支付(小程序)
前言 微信支付是企业级项目中经常使用到的功能,作为后端开发人员,完整地掌握该技术是十分有必要的. logo 一.申请流程和步骤 图1-1 注册微信支付账号 获取微信小程序APPID 获取微信商家的商户 ...
- 微信公众号红包接口开发PHP开发 CA证书出错,请登陆微信支付商户平台下载证书
微信红包接口调试过程中一直提示“CA证书出错,请登陆微信支付商户平台下载证书”,经反复调试,大致解决方法如下: 1.首先确保CA证书的路径是否正确,一定得是绝对路径,因为是PHP开发的,这里需要三个p ...
- 微信支付接口 H5
php微信支付若干问题记录 1.缺少参数$key0$ 此问题的可能性有几种,大致有1.timeStamp这个参数应该是string类型,默认time是int 2.确实是参数缺少 比如:prepay_ ...
- 微信支付配置信息,JSAPI接口,H5调用微信js接口支付,微信公众号支付
微信支付已经做完了,没接触过微信的我,经历了非常艰难的3天,才把微信支付给做出来,对于专业的人来说,估计就是一小时就搞定的事情了,虽然说做了很长时间,但是确实也学到东西了,也收获了不少,下面跟大家分享 ...
- php微信支付接口开发程序
php微信支付接口开发程序讲解 微信支付接口现在也慢慢的像支付宝一个可以利用api接口来实现第三方网站或应用进行支付了, 下文整理了一个php微信支付接口开发程序并且己测试,有兴趣的朋友可进入参考. ...
- php微信支付接口开发程序(一)
阅读对象 本文阅读对象:商户系统(在线购物平台.人工收银系统.自动化智能收银系统或其他)集成微信支付涉及的技术架构师,研发工程师,测试工程师,系统运维工程师. 支付模式 1. 刷卡支付 刷卡支付是用户 ...
随机推荐
- 为测试管理正名,华为云CodeArts TestPlan的守护之道
摘要:华为云CodeArts TestPlan既有公有云版本,也有下沉到私有云的版本. 本文分享自华为云社区<为测试管理正名,华为云CodeArts TestPlan的守护之道>,作者:云 ...
- [数据结构]普里姆(Prim)算法生成最小生成树
前提介绍:最小生成树概念 一个连通图的生成树是图的极小连通子图,它包含图中的所有定点,并且只含尽可能少的边,这意味着对于生成树来说,就砍去使生成树变成非连通图:若给它怎家一条边就会形成图中的一条回路. ...
- Java连接Zookeeper以及书写简单增删改查的方法
Java连接Zookeeper以及书写简单增删改查的方法 摘要:本笔记主要记录了使用IDEA创建一个Maven项目并使用Maven配置文件下载Zookeeper连接驱动,连接云服务器的Zookee ...
- Winform DataGridViewTextBoxCell 编辑添加右键菜单,编辑选中文本
如上是我们使用DataGridView时,编辑单元格右键会出现系统菜单.现在我们添加自己的右键菜单,并可以操作选中文字. DataGridViewTextBoxCell: DataGridViewTe ...
- 如何进行动态ip的域名解析设置?
如何进行动态ip的域名解析设置?目前,有一部分域名客户出于节省成本.技术验证等因素,会把自己家里或是部门的电脑用来当做Web服务器.mail服务器或是ftp服务器.如果想提供给其他人长期浏览,一般都要 ...
- continue语句-死循环
continue语句 continue 使用场景:结束本次循环,继续下一次的循环 public static void main(String[] args) { for (int i = 1; i ...
- jmeter性能监控
jmeter监控内存,CPU等方法 (2018-06-26 15:39:37) 转载▼ 分类: 性能测试 方法1:使用插件来监控CPU,内存等的使用情况1.需要的插件准备JMeterPlugins ...
- 一文详解数仓GaussDB(DWS) 函数出参带出方式
摘要:本文主要讲解DWS函数出参带出方式. 本文分享自华为云社区<GaussDB(DWS)功能 -- 函数出参 #[玩转PB级数仓GaussDB(DWS)]>,作者:譡里个檔 . DWS的 ...
- Activiti01-基本介绍
1.工作流的定义 工作流是将一组任务组织起来以完成某个有序的过程:定义了任务的触发顺序和触发条件,而且每个任务可以由一个或多个软件系统完成,也可以由一个或一组人完成, 还可以由一个或多个人与软件系统协 ...
- 2211-14MongoDB学习
学习资源来自菜鸟教程 MongoDB数据库 MongoDB概念解析 不管我们学习什么数据库都应该学习其中的基础概念,在mongodb中基本的概念是文档.集合.数据库,下面我们挨个介绍. 下表将帮助您更 ...