first commit
This commit is contained in:
338
金壶/ydyd_service/application/common/WxPay.php
Normal file
338
金壶/ydyd_service/application/common/WxPay.php
Normal file
@@ -0,0 +1,338 @@
|
||||
<?php
|
||||
namespace app\common;
|
||||
use Exception;
|
||||
use think\Db;
|
||||
use think\facade\Cache;
|
||||
use think\facade\Config;
|
||||
use think\facade\Env;
|
||||
use think\facade\Log;
|
||||
|
||||
require_once Env::get('extend_path').'wxpay/lib/WxPay.Api.php';
|
||||
require_once Env::get('extend_path').'wxpay/lib/WxPay.Notify.php';
|
||||
//require_once Env::get('extend_path').'wxpay/base/WxPay.NativePay.php';
|
||||
require_once Env::get('extend_path').'wxpay/base/log.php';
|
||||
require_once Env::get('extend_path').'wxpay/lib/WxPay.Config.Interface.php';
|
||||
class WxPay
|
||||
{
|
||||
public function __construct()
|
||||
{
|
||||
//初始化日志,微信支付方面的日志单独存放
|
||||
$logHandler= new \CLogFileHandler(Env::get('app_path')."WxPayLog/".date('Y-m-d').'.log');
|
||||
$log = \Log::Init($logHandler, 15);
|
||||
}
|
||||
|
||||
public function nativePay($pay_data) {
|
||||
$notify = new NativePay();
|
||||
//模式二
|
||||
/**
|
||||
* 流程:
|
||||
* 1、调用统一下单,取得code_url,生成二维码
|
||||
* 2、用户扫描二维码,进行支付
|
||||
* 3、支付完成之后,微信服务器会通知支付成功
|
||||
* 4、在支付成功通知中需要查单确认是否真正支付成功(见:notify.php)
|
||||
*/
|
||||
$input = new \WxPayUnifiedOrder();
|
||||
$input->SetBody("医点医滴-单号:".$pay_data['order_sn']);
|
||||
$input->SetAttach("自定义业务参数");
|
||||
$input->SetOut_trade_no($pay_data['pay_no']);
|
||||
$input->SetTotal_fee(number_format($pay_data['total_amount']*100,0,'.',''));
|
||||
$input->SetTime_start(date("YmdHis"));
|
||||
//$input->SetTime_expire(date("YmdHis", time() + 600));
|
||||
//$input->SetGoods_tag("test");
|
||||
$input->SetNotify_url(Config::get("WEB_ACCESS_CONFIG")["WXPAY_NOTIFY_URL"]);
|
||||
$input->SetTrade_type("NATIVE");
|
||||
$input->SetProduct_id($pay_data["order_sn"]);
|
||||
|
||||
$result = $notify->GetPayUrl($input);
|
||||
$pay_url = '';
|
||||
if (isset($result["code_url"])) {
|
||||
$pay_url = $result["code_url"];
|
||||
} else {
|
||||
\Log::ERROR(json_encode($result));
|
||||
}
|
||||
|
||||
if(substr($pay_url, 0, 6) == "weixin") {
|
||||
return $pay_url;
|
||||
}else{
|
||||
return false;
|
||||
//header('HTTP/1.1 404 Not Found');
|
||||
}
|
||||
}
|
||||
|
||||
public function makeQrcode($pay_url) {
|
||||
require_once Env::get('extend_path').'wxpay/base/phpqrcode/phpqrcode.php';
|
||||
return \QRcode::png($pay_url);
|
||||
}
|
||||
|
||||
public function nativeNotify() {
|
||||
$config = new WxPayConfig();
|
||||
\Log::DEBUG("扫码支付回调信息");
|
||||
$notify = new NativeNotifyCallBack();
|
||||
$notify->Handle($config, true);
|
||||
//为阻止TP发送调试信息
|
||||
exit;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
class NativePay
|
||||
{
|
||||
/**
|
||||
*
|
||||
* 生成扫描支付URL,模式一
|
||||
* @param BizPayUrlInput $bizUrlInfo
|
||||
*/
|
||||
public function GetPrePayUrl($productId)
|
||||
{
|
||||
$biz = new \WxPayBizPayUrl();
|
||||
$biz->SetProduct_id($productId);
|
||||
try{
|
||||
$config = new WxPayConfig();
|
||||
$values = \WxpayApi::bizpayurl($config, $biz);
|
||||
} catch(Exception $e) {
|
||||
\Log::ERROR(json_encode($e));
|
||||
}
|
||||
$url = "weixin://wxpay/bizpayurl?" . $this->ToUrlParams($values);
|
||||
return $url;
|
||||
}
|
||||
|
||||
/**
|
||||
*
|
||||
* 参数数组转换为url参数
|
||||
* @param array $urlObj
|
||||
*/
|
||||
private function ToUrlParams($urlObj)
|
||||
{
|
||||
$buff = "";
|
||||
foreach ($urlObj as $k => $v)
|
||||
{
|
||||
$buff .= $k . "=" . $v . "&";
|
||||
}
|
||||
|
||||
$buff = trim($buff, "&");
|
||||
return $buff;
|
||||
}
|
||||
|
||||
/**
|
||||
*
|
||||
* 生成直接支付url,支付url有效期为2小时,模式二
|
||||
* @param UnifiedOrderInput $input
|
||||
*/
|
||||
public function GetPayUrl($input)
|
||||
{
|
||||
if($input->GetTrade_type() == "NATIVE")
|
||||
{
|
||||
try{
|
||||
$config = new WxPayConfig();
|
||||
$result = \WxPayApi::unifiedOrder($config, $input);
|
||||
return $result;
|
||||
} catch(Exception $e) {
|
||||
\Log::ERROR($e->getTraceAsString());
|
||||
\Log::ERROR($e->errorMessage());
|
||||
}
|
||||
}
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
class WxPayConfig extends \WxPayConfigInterface
|
||||
{
|
||||
//=======【基本信息设置】=====================================
|
||||
public function GetAppId()
|
||||
{
|
||||
return 'wxb537be7613530d10';
|
||||
}
|
||||
|
||||
public function GetMerchantId()
|
||||
{
|
||||
return '1523746531';
|
||||
}
|
||||
|
||||
//=======【支付相关配置:支付成功回调地址/签名方式】===================================
|
||||
|
||||
/**
|
||||
* TODO:支付回调url
|
||||
* 签名和验证签名方式, 支持md5和sha256方式
|
||||
**/
|
||||
public function GetNotifyUrl()
|
||||
{
|
||||
return "";
|
||||
}
|
||||
|
||||
public function GetSignType()
|
||||
{
|
||||
return "HMAC-SHA256";
|
||||
}
|
||||
|
||||
//=======【curl代理设置】===================================
|
||||
|
||||
/**
|
||||
* TODO:这里设置代理机器,只有需要代理的时候才设置,不需要代理,请设置为0.0.0.0和0
|
||||
* 本例程通过curl使用HTTP POST方法,此处可修改代理服务器,
|
||||
* 默认CURL_PROXY_HOST=0.0.0.0和CURL_PROXY_PORT=0,此时不开启代理(如有需要才设置)
|
||||
* @var unknown_type
|
||||
*/
|
||||
public function GetProxy(&$proxyHost, &$proxyPort)
|
||||
{
|
||||
$proxyHost = "0.0.0.0";
|
||||
$proxyPort = 0;
|
||||
}
|
||||
|
||||
|
||||
//=======【上报信息配置】===================================
|
||||
|
||||
/**
|
||||
* TODO:接口调用上报等级,默认紧错误上报(注意:上报超时间为【1s】,上报无论成败【永不抛出异常】,
|
||||
* 不会影响接口调用流程),开启上报之后,方便微信监控请求调用的质量,建议至少
|
||||
* 开启错误上报。
|
||||
* 上报等级,0.关闭上报; 1.仅错误出错上报; 2.全量上报
|
||||
* @var int
|
||||
*/
|
||||
public function GetReportLevenl()
|
||||
{
|
||||
return 1;
|
||||
}
|
||||
|
||||
|
||||
//=======【商户密钥信息-需要业务方继承】===================================
|
||||
/*
|
||||
* KEY:商户支付密钥,参考开户邮件设置(必须配置,登录商户平台自行设置), 请妥善保管, 避免密钥泄露
|
||||
* 设置地址:https://pay.weixin.qq.com/index.php/account/api_cert
|
||||
*
|
||||
* APPSECRET:公众帐号secert(仅JSAPI支付的时候需要配置, 登录公众平台,进入开发者中心可设置), 请妥善保管, 避免密钥泄露
|
||||
* 获取地址:https://mp.weixin.qq.com/advanced/advanced?action=dev&t=advanced/dev&token=2005451881&lang=zh_CN
|
||||
* @var string
|
||||
*/
|
||||
public function GetKey()
|
||||
{
|
||||
return 'ad6abfe6e0fb3319f96e866fe7e33282';
|
||||
}
|
||||
|
||||
public function GetAppSecret()
|
||||
{
|
||||
return '817855ea57fdb7bfc1d60fc3b4a4aaa3';
|
||||
}
|
||||
|
||||
|
||||
//=======【证书路径设置-需要业务方继承】=====================================
|
||||
|
||||
/**
|
||||
* TODO:设置商户证书路径
|
||||
* 证书路径,注意应该填写绝对路径(仅退款、撤销订单时需要,可登录商户平台下载,
|
||||
* API证书下载地址:https://pay.weixin.qq.com/index.php/account/api_cert,下载之前需要安装商户操作证书)
|
||||
* 注意:
|
||||
* 1.证书文件不能放在web服务器虚拟目录,应放在有访问权限控制的目录中,防止被他人下载;
|
||||
* 2.建议将证书文件名改为复杂且不容易猜测的文件名;
|
||||
* 3.商户服务器要做好病毒和木马防护工作,不被非法侵入者窃取证书文件。
|
||||
* @var path
|
||||
*/
|
||||
public function GetSSLCertPath(&$sslCertPath, &$sslKeyPath)
|
||||
{
|
||||
$sslCertPath = Env::get('extend_path') . 'wxpay/cert/apiclient_cert.pem';
|
||||
$sslKeyPath = Env::get('extend_path') . 'wxpay/cert/apiclient_key.pem';
|
||||
}
|
||||
}
|
||||
|
||||
class NativeNotifyCallBack extends \WxPayNotify
|
||||
{
|
||||
public function unifiedorder($openId, $product_id)
|
||||
{
|
||||
//统一下单
|
||||
$config = new WxPayConfig();
|
||||
$input = new \WxPayUnifiedOrder();
|
||||
$input->SetBody("test");
|
||||
$input->SetAttach("test");
|
||||
$input->SetOut_trade_no($config->GetMerchantId().date("YmdHis"));
|
||||
$input->SetTotal_fee("1");
|
||||
$input->SetTime_start(date("YmdHis"));
|
||||
$input->SetTime_expire(date("YmdHis", time() + 600));
|
||||
$input->SetGoods_tag("test");
|
||||
$input->SetNotify_url("http://paysdk.weixin.qq.com/notify.php");
|
||||
$input->SetTrade_type("NATIVE");
|
||||
$input->SetOpenid($openId);
|
||||
//$input->SetProduct_id($product_id);
|
||||
try {
|
||||
$result = \WxPayApi::unifiedOrder($config, $input);
|
||||
\Log::DEBUG("unifiedorder:" . json_encode($result));
|
||||
} catch(Exception $e) {
|
||||
\Log::ERROR(json_encode($e));
|
||||
}
|
||||
return $result;
|
||||
}
|
||||
|
||||
/**
|
||||
*
|
||||
* 回包前的回调方法
|
||||
* 业务可以继承该方法,打印日志方便定位
|
||||
* @param string $xmlData 返回的xml参数
|
||||
*
|
||||
**/
|
||||
public function LogAfterProcess($xmlData)
|
||||
{
|
||||
\Log::DEBUG("返回响应数据, return xml:" . $xmlData);
|
||||
return;
|
||||
}
|
||||
|
||||
/**
|
||||
* @param WxPayNotifyResults $objData 回调解释出的参数
|
||||
* @param WxPayConfigInterface $config
|
||||
* @param string $msg 如果回调处理失败,可以将错误信息输出到该方法
|
||||
* @return true回调出来完成不需要继续回调,false回调处理未完成需要继续回调
|
||||
*/
|
||||
public function NotifyProcess($objData, $config, &$msg)
|
||||
{
|
||||
$data = $objData->GetValues();
|
||||
//echo "处理回调";
|
||||
//TODO 1、进行参数校验
|
||||
//if(!array_key_exists("openid", $data) ||!array_key_exists("product_id", $data))
|
||||
if(!array_key_exists("openid", $data) || !array_key_exists("out_trade_no", $data))
|
||||
{
|
||||
$msg = "回调数据异常";
|
||||
\Log::DEBUG($msg . json_encode($data));
|
||||
return false;
|
||||
}
|
||||
|
||||
//TODO 2、进行签名验证
|
||||
try {
|
||||
$checkResult = $objData->CheckSign($config);
|
||||
if($checkResult == false){
|
||||
//签名错误
|
||||
\Log::ERROR("签名错误...");
|
||||
return false;
|
||||
}
|
||||
} catch(Exception $e) {
|
||||
\Log::ERROR(json_encode($e));
|
||||
}
|
||||
|
||||
Log::info('回调返回数据'.json_encode($data));
|
||||
//处理业务逻辑
|
||||
|
||||
$this->SetData("result_code", "SUCCESS");
|
||||
$this->SetData("err_code_des", "OK");
|
||||
|
||||
//$openid = $data["openid"];
|
||||
//$product_id = $data["product_id"];
|
||||
|
||||
//TODO 3、处理业务逻辑
|
||||
/*//统一下单,不知道样例里在做什么,响应参数里不需要这些值了
|
||||
$result = $this->unifiedorder($openid, $product_id);
|
||||
\Log::DEBUG('回调结果数据'. json_encode($data));
|
||||
if(!array_key_exists("appid", $result) ||
|
||||
!array_key_exists("mch_id", $result) ||
|
||||
!array_key_exists("prepay_id", $result))
|
||||
{
|
||||
$msg = "统一下单失败";
|
||||
\Log::DEBUG($msg . json_encode($data));
|
||||
return false;
|
||||
}
|
||||
|
||||
$this->SetData("appid", $result["appid"]);
|
||||
$this->SetData("mch_id", $result["mch_id"]);
|
||||
$this->SetData("nonce_str", \WxPayApi::getNonceStr());
|
||||
$this->SetData("prepay_id", $result["prepay_id"]);
|
||||
$this->SetData("result_code", "SUCCESS");
|
||||
$this->SetData("err_code_des", "OK");
|
||||
return true;*/
|
||||
}
|
||||
}
|
||||
Reference in New Issue
Block a user