sifangpay/app/ServicePay/XianYuPayServices.php

289 lines
9.7 KiB
PHP
Raw Blame History

This file contains ambiguous Unicode characters

This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.

<?php
namespace App\ServicePay;
use App\Models\Merchant;
use App\Models\Order;
use Illuminate\Support\Facades\Log;
use Illuminate\Support\Collection;
use Illuminate\Http\Request;
use Ixudra\Curl\Facades\Curl;
class XianYuPayServices implements PayApiInterface
{
use PayTrait;
use ThirdPaySignTrait;
public $gateway_list;//当前类型的支付通道列表
public $pay_type;//支付类型
public $pay_method;//支付方法
public $pay_gateway;//当前的支付通道实例
public $pay_config;//这个通道的支付配置信息
public $order;
public $request;
public $gateway_id;
public $pay_data;
public $log_name;
public $result_data;
public static $result;
//支付发起第一步取得通道getGateway随机通道第二部配置支付信息payConfig,第三部发起支付
//第二部配置支付信息payConfig
public function payConfig($type, $setConfig = [])
{
$config = [
'url'=>'http://jhapi.ua2ul5.cn/Pay_Index.html',
'debug' => 1,//调试
'logDir' => to_linux_path(storage_path() . '/logs/'),
'mch_id' => $this->pay_gateway['app_id'], //客户交易者账号
'token' => $this->pay_gateway['app_key'],
'interface' => $this->pay_gateway['mch_id'],
'return_url' => action('Pay\PayController@returnNotify', ['type' => $type]),
'notify_url' => action('Pay\PayController@notify', ['type' => $type]),
];
$this->pay_config = $config;
}
//统一下单支付
public function pay($pay_data)
{
//商户号
$accountId = $this->pay_config['mch_id'];
//商户秘钥
$key = $this->pay_config['token'];
$payData = [
'pay_memberid' => $accountId,//商户
'pay_orderid' => strval($pay_data['out_trade_no']),//订单号
'pay_applydate' => date('Y-m-d H:i:s'),//提交时间
'pay_productname' => mt_rand(100000, 999999), //商品名称
'pay_amount' => intval($pay_data['total_amount']), //订单金额(元)
'pay_bankcode' => $this->pay_gateway['mch_id'],//对应的三方通道
'pay_notifyurl' => strval($this->pay_config['notify_url']),// //异步回调地址
'pay_callbackurl' => strval($this->pay_config['return_url']),// //页面跳转通知
];
$sign = $this->md5Verify('create',$payData, $key, ['pay_productname']);//签名
$payData['pay_md5sign'] = $sign;
$this->debugLog('下单接口请求内容'.json_encode($payData,true), []);
$res = Curl::to($this->pay_config['url'])->withData($payData)->post();
// $this->debugLog('下单接口返回' . is_array($res) ? json_encode($res, true) : json_encode(json_decode($res, 256), true));
return $res;
}
/**
* 检查订单
* @param $orderid
* @return bool|string
*/
private function checkOrder($orderid){
$url = 'http://jhapi.ua2ul5.cn/Pay_Trade_query.html';
$payData['pay_memberid'] = $this->pay_gateway['app_id'];
$payData['pay_orderid'] = $orderid;
$key = $this->pay_config['token'];
$sign = $this->md5Verify('check', $payData, $key);
$payData['pay_md5sign'] = $sign;
Log::channel('pay_order')->info('查询接口请求', $payData);
$res = Curl::to($url)->withData($payData)->post();
$res = is_array($res) ? $res : json_decode($res, 256);
// $this->debugLog('查询接口返回' . is_array($res) ? json_encode($res, true) : json_encode(json_decode($res, 256), true));
Log::channel('pay_order')->info('查询接口返回', $res);
if (isset($res['returncode']) && $res['returncode'] == '00') {
if ($res['data']['trade_state'] == 'SUCCESS' && $res['data']['orderid']==$orderid) {
return true;
}
}
return false;
}
//统一验证签名
public function verify()
{
$para = $this->result_data;
$sign = $para['sign'];
unset($para['sign']);
$token = $this->pay_config['token'];
$md5sign = $this->md5Verify('check',$para, $token,['sign','attach']);
if ($md5sign == $sign) {
return true;
} else {
return false;
}
}
//返回给支付商的成功
public function success()
{
echo 'OK';exit;
}
//统一回调处理
/**
* 回调第一部,如果是同步,直接回传
* @param $return
* @param $pay_type
* @param $request
* @return bool|\Illuminate\Http\RedirectResponse
*/
public function notify($return, $pay_type, $request)
{
$this->setLogName($pay_type);
Log::channel('pay_order')->info('回调原始数据', $request->all());
$this->pay_type = $pay_type;
$this->request = $request;
//取得订单,是否有此订单,如果没有直接返回空
$order_sn = $request->input('orderid');
$ip=request()->getClientIp();
if ($ip != '47.91.252.231') {
$this->debugLog('IP不合法', $ip);
return 'fail';
}
//检查回调订单状态
//判断有没支付成功先,没有的话,直接就没有下一步了
$pay_status = $request->input('returncode');
if ($pay_status != '00') {
$this->debugLog('订单支付失败', $this->request->all());
return '订单支付失败';
}
//取得订单
$this->getOrder($order_sn);
$return = ($return) ? 1 : 0;
if ($return) {
//判断是否是商户id
if ($this->order->merchant_id == 0) {
return redirect()->route('web.user.index');
}
//
return $this->merchantReturnSend();
}
/* $this->order = Order::where('order_sn', $order_sn)->first();
if(empty($this->order))
{
return false;
}*/
//取得通道id
$this->gateway = $this->pay_gateway = config('gateway.config')[$this->gateway_id];
//dd($this->gateway);
//取得支付配置
$this->payConfig($this->pay_type);
$this->result_data = $request->all();
//检查三方的订单
$checkorder = $this->checkOrder($order_sn);
if (!$checkorder) {
$this->debugLog('三方订单未支付成功');
return '三方订单未支付成功';
}
//dump($this->result_data);
//进行验证签名
if (!$this->verify()) {
$this->debugLog('签名验证失败');
return '签名验证失败';
}
return $this->payNotify();
}
/**
* 同步回调
* @return \Illuminate\Http\RedirectResponse
*/
public function returnPay()
{
//判断是否是商户id
if ($this->order->merchant_id == 0) {
return redirect()->route('web.user.index');
}
//
return $this->merchantReturnSend();
}
//异步回调
/**
* 获得通道信息,取得支付配置模型,验证签名,
* @return bool|void
*/
private function payNotify()
{
//取得通道信息内容
//dd($this->result_data);
$data = $this->result_data;
$this->pay_data = $this->result_data;
//如果应答状态不是01/A6表示支付失败
// $this->debugLog(json_encode($data,true));
$this->debugLog('-------------' . $this->order->order_sn . '--选择----' . $this->pay_type . '----' . $this->pay_method . '----开始回调处理-------------------------');
if (empty($data)) {
return $this->debugLog('验证签名失败', $data);
}
try {
$pay_cn_name = '';
//统一格式化
$this->unionHandle($data);
//支付返回信息
$this->pay_data = $data;
$this->debugLog('验证签名成功,数据', $data);
//更新订单
$this->updateOrder();
$this->debugLog('updateOrder Ok');
} catch (\Exception $exception) {
$this->debugLog('失败异常内容:' . $exception->getMessage());
if (!in_array($data['respCode'], ['00', 'A6'])) {
$this->debugLog('订单支付失败', $this->request->all());
return '支付失败';//支付失败
}
$this->order->notify_status = 1;//支付回调成功
$this->order->pay_status = 1;//支付状态
$this->order->pay_ok_at = date('Y-m-d H:i:s');
$this->order->save();//保存
Log::channel('pay_success')->info($pay_cn_name . '支付成功,但处理订单失败', ['data' => json_encode($data)]);
}
}
/**
* 统一格式化
*/
public function unionHandle($data)
{
$result = [
'order_sn' => $data['orderid'],//我方订单号
'pay_order_sn' => $data['transaction_id'],//三方的订单号
'pay_money' => $data['amount'],
'transaction_id' => $data['transaction_id'],
'returncode' => $data['returncode'],
'pay_type' => 'xuanyupay_alipay',
'account' => ''
];
$this->setResult($result);
Log::channel('pay_success')->info('支付成功', [
'pay_type' => $result['pay_type'], 'pay_money' => $result['pay_money'],
'account' => $result['account'], 'order_sn' => $result['order_sn'],
'pay_order_sn' => $result['pay_order_sn']]);
}
/**
* 这个调试需要配置在config/logging.php
* @param $pay_type
*/
public function setLogName($pay_type)
{
$name = 'xianyupay_';
$this->log_name = $name;
}
}