love_php/app/Services/WechatService.php
2026-04-02 09:20:51 +08:00

1946 lines
75 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\Services;
use App\Models\Server\WechatSubMerchant;
use GuzzleHttp\Client;
use Illuminate\Support\Facades\Redis;
use Log;
use Carbon\Carbon;
use App\Repositories\Eloquent\SmsRepository as Sms;
use EasyWeChat;
use EasyWeChat\Factory;
use App\Utils\Messenger;
use App\Models\Live\Viewer;
use EasyWeChat\Payment\Order;
Use App\Utils\Http;
use App\Models\Wechat;
use App\Models\PayLog;
use App\Models\Order as LoveOrder;
use App\Models\TemplateMsgLog;
use App\Http\Response\ResponseJson;
use Exception;
use Illuminate\Validation\Rules\Exists;
use App\Models\Server\TouristOrder;
use EasyWeChat\Kernel\Support;
use WeChatPay\Builder;
use WeChatPay\Crypto\Rsa;
use WeChatPay\Formatter;
use WeChatPay\Util\PemUtil;
use WeChatPay\Util\MediaUtil;
class WechatService
{
use ResponseJson;
protected $sms;
protected $app;
protected $official_app;
// protected $instance;
/*
* 构造函数
*/
public function __construct(Sms $sms)
{
$mini_config = [
'app_id' => config('wechat.mini_program.app_id'),
'secret' => config('wechat.mini_program.secret'),
];
// $official_config = [
// 'app_id' => config('wechat.app_id'),
// 'secret' => config('wechat.secret'),
// ];
// $app = Factory::miniProgram($mini_config);
$app = \EasyWeChat::miniProgram();
$official_app = \EasyWeChat::officialAccount('new');
$this->app = $app;
$this->official_app = $official_app;
$this->sms = $sms;
Carbon::setLocale('zh');
}
public function officialApp($param='new')
{
$official_app = \EasyWeChat::officialAccount($param);
return $official_app;
}
/**
* 是否关注公众号
*/
public function officialIsSubscribed($openid)
{
$app = \WechatService::officialApp();
if(!$openid){
return 0;
}
$wechatUser = $app->user->get($openid);
$result = !empty($wechatUser)&&isset($wechatUser['subscribe']);
$is_subscribe = $result?$wechatUser['subscribe']:0;
return $is_subscribe;
}
public function paymentInstance()
{
$merchantId = config('wechat.service_payment.mch_id');
// 从本地文件中加载「商户API私钥」「商户API私钥」会用来生成请求的签名
$merchantPrivateKeyFilePath = 'file://'.config('wechat.service_payment.key_path');
$merchantPrivateKeyInstance = Rsa::from($merchantPrivateKeyFilePath, Rsa::KEY_TYPE_PRIVATE);
// 「商户API证书」的「证书序列号」
$merchantCertificateSerial = config('wechat.service_payment.serial');
// 从本地文件中加载「微信支付平台证书」,用来验证微信支付应答的签名
$platformCertificateFilePath = 'file://'.config('wechat.service_payment.cert_path');
$platformPublicKeyInstance = Rsa::from($platformCertificateFilePath, Rsa::KEY_TYPE_PUBLIC);
// 从「微信支付平台证书」中获取「证书序列号」
$platformCertificateSerial = PemUtil::parseCertificateSerialNo($platformCertificateFilePath);
// 构造一个 APIv3 客户端实例
$instance = Builder::factory([
'mchid' => $merchantId,
'serial' => $merchantCertificateSerial,
'privateKey' => $merchantPrivateKeyInstance,
'certs' => [
$platformCertificateSerial => $platformPublicKeyInstance,
],
]);
return $instance;
}
public function app(){
return $this->app;
}
public function server()
{
$this->official_app->server->push(function ($message) {
// $message['FromUserName'] // 用户的 openid
// $message['MsgType'] // 消息类型event, text....
return "您好!欢迎使用 EasyWeChat";
});
// 在 laravel 中:
$response = $this->official_app->server->serve();
// $response 为 `Symfony\Component\HttpFoundation\Response` 实例
// 对于需要直接输出响应的框架,或者原生 PHP 环境下
$response->send();
// 而 laravel 中直接返回即可:
return $response;
}
//通用发短信任务
public function sentMessage($mobile, $message)
{
$this->sms->sentMessage( $mobile, $message);
}
public function constructWXH5Pay($pay_order, $user_id, $detail, $activity_id=null,$callback='')
{
$spbill_create_ip = $this->getClientIp();
// $spbill_create_ip = $_SERVER['REMOTE_ADDR'];
// $spbill_create_ip = '113.97.32.78';
if(!$callback)
$callback = config('app.url').'/api/mark/order/pay/'.$pay_order['trade_no'];
$attributes = array(
'trade_type' => 'MWEB', // JSAPINATIVEAPP...
'body' => $detail,
'detail' => $detail,
'out_trade_no' => $pay_order['trade_no'],
'total_fee' => ($pay_order['cash']*100),
'notify_url' => $callback, // 支付结果通知网址,如果不设置则会使用配置里的默认地址
'spbill_create_ip' => $spbill_create_ip,
);
if ($detail == '购买认证') {
$redirect_url = env('APP_URL').'/mobile/#/authentication';
}elseif ($detail == '会员充值') {
$redirect_url = env('APP_URL').'/mobile/#/upgrade';
}elseif ($detail == '参加活动') {
$redirect_url = env('APP_URL').'/mobile/#/activityDetail/'.$activity_id;
}elseif ($detail == '福恋约见') {
$redirect_url = env('APP_URL').'/mobile/#/';
}elseif ($detail == '奉献金') {
$redirect_url = env('APP_URL').'/mobile/#/';
}elseif ($detail == '购买课程') {
$redirect_url = env('APP_URL').'/mobile/#/';
}
$result = $this->officialPay($attributes, $redirect_url);
return $result;
}
public function constructWXPay($pay_order, $user_id, $detail='福币充值',$callback='')
{
$openid = Wechat::where('user_id', $user_id)->value('openid');
if(!$openid)
$openid = Viewer::where('user_id', $user_id)->value('openid');
if(!$callback)
$callback = config('app.url').'/api/mark/order/pay/'.$pay_order['trade_no'];
$attributes = array(
'trade_type' => 'JSAPI', // JSAPINATIVEAPP...
'body' => $detail,
'detail' => $detail,
'out_trade_no' => $pay_order['trade_no'],
'total_fee' => ($pay_order['cash']*100),
'notify_url' => $callback, // 支付结果通知网址,如果不设置则会使用配置里的默认地址
'openid' => $openid,
);
$result = $this->pay($attributes);
return $result;
}
public function constructMiniPay($trade_no, $openid, $total_fee, $body, $detail, $callback)
{
$attributes = array(
'trade_type' => 'JSAPI', // JSAPINATIVEAPP...
'body' => $body,
'detail' => $detail,
'out_trade_no' => $trade_no,
'total_fee' => ($total_fee*100),
'notify_url' => $callback, // 支付结果通知网址,如果不设置则会使用配置里的默认地址
'openid' => $openid,
);
$result = $this->pay($attributes);
return $result;
}
public function constructSWXPay($order, $openid, $detail='',$callback='')
{
$attributes = array(
'trade_type' => 'JSAPI', // JSAPINATIVEAPP...
'body' => $detail,
'detail' => '打赏金额:'.$order['price'],
'out_trade_no' => $order['trade_no'],
'total_fee' => ($order['price']*100),
'notify_url' => $callback, // 支付结果通知网址,如果不设置则会使用配置里的默认地址
'openid' => $openid,
);
$result = $this->officialPay($attributes);
return $result;
}
public function constructSWXServicePay($order, $openid, $body, $detail, $callback)
{
$attributes = array(
'trade_type' => 'JSAPI', // JSAPINATIVEAPP...
'body' => $body,
'detail' => $detail,
'out_trade_no' => $order['trade_no'],
'total_fee' => ($order['price']*100),
'notify_url' => $callback, // 支付结果通知网址,如果不设置则会使用配置里的默认地址
'openid' => $openid,
);
return $attributes;
}
public function constructWXAppPay($pay_order, $user_id, $detail="福币充值", $callback='',$link=false)
{
$spbill_create_ip = $this->getClientIp();
$attributes = array(
'trade_type' => 'APP', // JSAPINATIVEAPP...
'body' => '福币充值',
'detail' => '福币充值',
'out_trade_no' => $pay_order['trade_no'],
'total_fee' => ($pay_order['cash']*100),
'notify_url' => $callback, // 支付结果通知网址,如果不设置则会使用配置里的默认地址
'spbill_create_ip' => $spbill_create_ip,
);
$PayLog = new PayLog;
$PayLog->type = 'activity';
$PayLog->user_id = $user_id;
$PayLog->trade_no =$pay_order['trade_no']??'';
$PayLog->remark = $callback;
$PayLog->save();
$result = $this->appPay($attributes,$link);
return $result;
}
public function isLovePay()
{
return true;
$ios_version = request()->header('app-version');
$and_version = request()->header('version-name');
//\Log::info($ios_version);
//\Log::info($and_version);
if(request()->header('ios_version') || request()->header('and_version')) {
return true;
}
$ios_arr = explode('.', $ios_version);
$and_arr = explode('.', $and_version);
if ($ios_version) {
if ($ios_arr[0] > 1) {
return true;
}elseif ($ios_arr[0] >= 1 && $ios_arr[1] > 3) {
return true;
}elseif ($ios_arr[0] >= 1 && $ios_arr[1] >= 3 && $ios_arr[2] >= 8) {
return true;
}
}
if ($and_version) {
if ($and_arr[0] > 1) {
return true;
}elseif ($and_arr[0] >= 1 && $and_arr[1] > 3) {
return true;
}elseif ($and_arr[0] >= 1 && $and_arr[1] >= 3 && $and_arr[2] >= 13) {
return true;
}
}
return false;
}
public function appPay($attributes,$link=false)
{
$attributes['body'] = mb_substr($attributes['body'], 0, 42, 'utf-8');
//新版本换成福恋智能
if(!$link){
$love_pay = $this->isLovePay();
}else{
$love_pay = true;
}
if ($love_pay) {
$config = config('wechat.payment');
}else{
//旧版本用友福同享
$config = config('wechat.ufutx_payment');
}
$config = config('wechat.payment');
$config['app_id'] = config('wechat.love_app_id');
$config['notify_url'] = $attributes['notify_url'];
$config['body'] = '福币充值';
$payment = Factory::payment($config);
$result = $payment->order->unify($attributes);
// $jssdk = $payment->jssdk;
$prepayId = '';
$code_url = null;
if ($result['return_code'] == 'SUCCESS' && $result['result_code'] == 'SUCCESS'){
$prepayId = $result['prepay_id'];
$result = $payment->jssdk->appConfig($prepayId);//第二次签名
} else {
}
return array(
'config' => $result,
'attributes' => $attributes,
);
}
public function getClientIp() {
if(getenv('HTTP_CLIENT_IP') && strcasecmp(getenv('HTTP_CLIENT_IP'), 'unknown')) {
$ip = getenv('HTTP_CLIENT_IP');
} elseif(getenv('HTTP_X_FORWARDED_FOR') && strcasecmp(getenv('HTTP_X_FORWARDED_FOR'), 'unknown')) {
$ip = getenv('HTTP_X_FORWARDED_FOR');
} elseif(getenv('REMOTE_ADDR') && strcasecmp(getenv('REMOTE_ADDR'), 'unknown')) {
$ip = getenv('REMOTE_ADDR');
} elseif(isset($_SERVER['REMOTE_ADDR']) && $_SERVER['REMOTE_ADDR'] && strcasecmp($_SERVER['REMOTE_ADDR'], 'unknown')) {
$ip = $_SERVER['REMOTE_ADDR'];
} else {
$ip = '0.0.0.0';
}
return preg_match('/[\d\.]{7,15}/', $ip, $matches) ? $matches[0] : '';
}
public function officialPay($attributes, $redirect_url='')
{
try {
$attributes['body'] = mb_substr($attributes['body'], 0, 42, 'utf-8');
if(config('wechat.payment.debug')){
return [
// 'js'=> $this->app->js->config(['chooseWXPay']),
'config'=>[
"appId"=> "wxc41491431733671e",
"nonceStr"=> "5cab16345cfbd",
"package"=> "prepay_id=wx081736523006918b9335320e1318134367",
"paySign"=> "394FBA790DD24032EFBD54122FF1373B",
"signType"=> "MD5",
"timestamp"=> "1554716212",
],
'attributes'=>$attributes,
'pay_qrcode'=>'http://shop.ufutx.com/qrcode/pay/wx20170606161524da84bf4e090195877403',
];
}
$config = config('wechat.payment');
$config['app_id'] = config('wechat.official_account.new.app_id');
$config['notify_url'] = $attributes['notify_url'];
$payment = Factory::payment($config);
$result = $payment->order->unify($attributes);
$jssdk = $payment->jssdk;
$prepayId = '';
$code_url = null;
if ($result['return_code'] == 'SUCCESS' && $result['result_code'] == 'SUCCESS'){
$prepayId = $result['prepay_id'];
// 这个很重要。有了这个才能调用支付。
// if($attributes['trade_type'] == 'NATIVE'){
// // $code_url = $this->generatePayQrCode($result['code_url'], $prepayId);
// $code_url = $result['code_url'];
// }
} else {
throw new \Exception($result['err_code_des']??'支付失败', 1);
}
$config = $jssdk->sdkConfig($prepayId); // 这个方法是取得js里支付所必须的参数用的。 没这个啥也做不了除非你自己把js的参数生成一遍
return array(
'config' => $config,
'attributes' => $attributes,
'mweb_url' => isset($result['mweb_url'])?$result['mweb_url'].'&redirect_url='.urlencode($redirect_url):'',
);
} catch (\Exception $e) {
$this->getError($e);
return false;
}
}
/**
* 服务商下单
* @param $attributes
* @param $sub_merchant_id
* @param null $is_share 是否启用分帐
* @return array|false
*/
public function officialServicePay($attributes, $sub_merchant_id,$is_share = null)
{
try {
$config = config('wechat.service_payment');
$config['notify_url'] = $attributes['notify_url'];
if($is_share){
$attributes['profit_sharing'] = 'Y';
}
$app = Factory::payment($config);
$app->setSubMerchant($sub_merchant_id);
$result = $app->order->unify($attributes);
if ($result['return_code'] == 'SUCCESS' && $result['result_code'] == 'SUCCESS'){
$config['appId'] = config('wechat.official_account.new.app_id');
$prepayId = $result['prepay_id'];
$jssdk = $app->jssdk;
$config = $jssdk->sdkConfig($prepayId);
}else{
$attributes = $result;
}
return ['config'=>$config, 'attributes'=>$attributes];
} catch (Exception $e) {
$this->getError($e);
return false;
}
}
public function pay($attributes)
{
try {
$attributes['body'] = mb_substr($attributes['body'], 0, 42, 'utf-8');
$config = config('wechat.payment');
$config['app_id'] = config('wechat.mini_program.app_id');
$config['notify_url'] = $attributes['notify_url'];
if(config('wechat.payment.debug')){
return array(
'config' => $config,
'attributes' => $attributes,
'mweb_url' => '',
);
}
$payment = Factory::payment($config);
$result = $payment->order->unify($attributes);
$jssdk = $payment->jssdk;
$prepayId = '';
$code_url = null;
if ($result['return_code'] == 'SUCCESS' && $result['result_code'] == 'SUCCESS'){
$prepayId = $result['prepay_id'];
// 这个很重要。有了这个才能调用支付。
// if($attributes['trade_type'] == 'NATIVE'){
// // $code_url = $this->generatePayQrCode($result['code_url'], $prepayId);
// $code_url = $result['code_url'];
// }
} else {
throw new \Exception($result['err_code_des']??'支付失败', 1);
}
$config = $jssdk->sdkConfig($prepayId); // 这个方法是取得js里支付所必须的参数用的。 没这个啥也做不了除非你自己把js的参数生成一遍
return array(
// 'js' => $this->app->js->config(['chooseWXPay']),
'config' => $config,
'attributes' => $attributes,
'mweb_url' => isset($result['mweb_url'])?$result['mweb_url']:'',
);
} catch (\Exception $e) {
$this->getError($e);
return false;
}
}
//发红包
public function sendNormalRedPack($trade_no, $send_name, $total_amount, $openid, $wishing, $act_name, $remark='')
{
if(config('wechat.payment.debug')){
return true;
}
$config = config('wechat.payment');
$config['app_id'] = config('wechat.app_id');
$payment = Factory::payment($config);
$redpack = $payment->redpack;
$redpackData = [
'mch_billno' => $trade_no,
'send_name' => $send_name,
're_openid' => $openid,
'total_num' => 1, //固定为1可不传
'total_amount' => $total_amount, //单位为分不小于100
'wishing' => $wishing,
// 'client_ip' => '192.168.0.1', //可不传,不传则由 SDK 取当前客户端 IP
'act_name' => $act_name,
'remark' => $remark,
// ...
];
// \Log::info($redpackData);
// \Log::info($config);
$result = $redpack->sendNormal($redpackData);
if($result['return_code'] == 'SUCCESS' && $result['result_code'] == 'SUCCESS'){
return true;
}else{
//\Log::info($trade_no.'红包订单错误'.json_encode($result));
// $this->sms->sentMessage('15872844805', $trade_no.'订单转账错误, 错误原因');
return false;
}
return ;
}
public static function sendNormalRedPackV2($trade_no, $send_name, $total_amount, $openid, $wishing, $act_name='', $remark='')
{
if(config('wechat.payment.debug')){
return true;
}
try {
$config = config('wechat.payment');
$config['app_id'] = config('wechat.app_id');
$payment = Factory::payment($config);
$redpack = $payment->redpack;
$redpackData = [
'mch_billno' => $trade_no,
'send_name' => $send_name,
're_openid' => $openid,
'total_num' => 1, //固定为1可不传
'total_amount' => $total_amount, //单位为分不小于100
'wishing' => $wishing,
// 'client_ip' => '192.168.0.1', //可不传,不传则由 SDK 取当前客户端 IP
'act_name' => $act_name,
'remark' => $remark,
// ...
];
$result = $redpack->sendNormal($redpackData);
if($result['return_code'] == 'SUCCESS' && $result['result_code'] == 'SUCCESS'){
return true;
}else{
//\Log::info($trade_no.'红包订单错误'.json_encode($result));
return $result;
// $this->sms->sentMessage('15872844805', $trade_no.'订单转账错误, 错误原因');
// return false;
}
} catch (Exception $e) {
// $this->sms->sentMessage('15872844805', $trade_no.'红包订单错误');
// \Log::debug($trade_no.'红包订单错误:'.$e->getMessage());
return false;
}
return false;
}
//发红包
public function sendGroupRedPack($trade_no, $send_name, $total_num=3, $total_amount, $openid, $wishing, $act_name='', $remark='')
{
$config = config('wechat.payment');
$config['app_id'] = config('wechat.app_id');
$payment = Factory::payment($config);
$redpack = $payment->redpack;
$redpackData = [
'mch_billno' => $trade_no,
'send_name' => $send_name,
're_openid' => $openid,
'total_num' => $total_num, //固定为1可不传
'total_amount' => $total_amount, //单位为分不小于100
'wishing' => $wishing,
// 'client_ip' => '192.168.0.1', //可不传,不传则由 SDK 取当前客户端 IP
'act_name' => $act_name,
'remark' => $remark,
// ...
];
$result = $redpack->sendGroup($redpackData);
if($result['return_code'] == 'SUCCESS' && $result['result_code'] == 'SUCCESS'){
return true;
// $this->sms->sentMessage('15872844805', '裂变红包发送成功');
}else{
//\Log::info($trade_no.'红包订单错误'.json_encode($result));
return $result;
// $this->sms->sentMessage('15872844805', $trade_no.'订单转账错误, 错误原因');
//$this->sms->sentMessage('15872844805', $trade_no.'红包发送失败, 错误原因'.$result['return_msg'].'业务结果'.$result['result_code']);
return false;
}
return false;
}
public static function checkNormalRedPack($trade_no=1576766055175987)
{
$res = (object)null;
$config = config('wechat.payment');
$config['app_id'] = config('wechat.app_id');
$app = Factory::payment($config);
$result = $app->transfer->queryBalanceOrder($trade_no);
$res->result = $result;
$res->status = false;
if($result['return_code'] == 'SUCCESS' && $result['result_code'] == 'SUCCESS'){
$res->status = true;
}else{
//\Log::info($trade_no.'红包订单错误'.json_encode($result));
// $this->sms->sentMessage('15872844805', $trade_no.'订单转账错误, 错误原因');
}
return $res;
}
//企业付款 小程序
public static function userTransfer($trade_no, $openid, $amount, $desc)
{
//\Log::info('transfer2');
//测试不检查
if(config('wechat.payment.debug')){
return true;
}
try {
$config = config('wechat.payment');
$config['app_id'] = config('wechat.mini_program.app_id');
$app = Factory::payment($config);
$arr = [
'partner_trade_no' => $trade_no, // 商户订单号,需保持唯一性(只能是字母或者数字,不能包含有符号)
'openid' => $openid,
'check_name' => 'NO_CHECK', // NO_CHECK不校验真实姓名, FORCE_CHECK强校验真实姓名
// 're_user_name' => '王小帅', // 如果 check_name 设置为FORCE_CHECK则必填用户真实姓名
'amount' => $amount, // 企业付款金额,单位为分
'desc' => $desc, // 企业付款操作说明信息。必填
];
$result = $app->transfer->toBalance($arr);
// dd($result);
if($result['return_code'] == 'SUCCESS' && $result['result_code'] == 'SUCCESS'){
return true;
}else{
//\Log::info($result);
//\Log::info($trade_no.'订单转账错误, 错误返回码'.json_encode($result));
// $this->sms->sentMessage('15872844805', $trade_no.'订单转账错误, 错误原因');
return false;
}
} catch (\Exception $e) {
// $this->sms->sentMessage('15872844805', $trade_no.'订单转账错误');
\Log::debug($trade_no.'订单转账错误:'.$e->getMessage());
return false;
}
}
//企业付款 公众号
public function officialUserTransfer($trade_no, $openid, $amount, $desc)
{
//\Log::info('transfer2');
//测试不检查
if(config('wechat.payment.debug')){
return true;
}
$app_id = config('wechat.app_id');
$result = $this->transfer($app_id, $trade_no, $openid, $amount, $desc);
return $result;
}
public function transfer($app_id, $trade_no, $openid, $amount, $desc)
{
try {
$config = config('wechat.payment');
$config['app_id'] = $app_id;
$app = Factory::payment($config);
$arr = [
'partner_trade_no' => $trade_no, // 商户订单号,需保持唯一性(只能是字母或者数字,不能包含有符号)
'openid' => $openid,
'check_name' => 'NO_CHECK', // NO_CHECK不校验真实姓名, FORCE_CHECK强校验真实姓名
// 're_user_name' => '王小帅', // 如果 check_name 设置为FORCE_CHECK则必填用户真实姓名
'amount' => $amount, // 企业付款金额,单位为分
'desc' => $desc, // 企业付款操作说明信息。必填
];
$result = $app->transfer->toBalance($arr);
// dd($res)
if($result['return_code'] == 'SUCCESS' && $result['result_code'] == 'SUCCESS'){
return null;
}else{
//\Log::info($trade_no.'订单转账错误, 错误返回码'.json_encode($result));
// $this->sms->sentMessage('15872844805', $trade_no.'订单转账错误, 错误原因');
return $result;
}
} catch (Exception $e) {
$this->sms->sentMessage('15872844805', $trade_no.'订单转账错误');
\Log::debug($trade_no.'订单转账错误:'.$e->getMessage());
return true;
}
}
//企业付款 公众号
public function officialUserTransferV2($trade_no, $openid, $amount, $desc)
{
//\Log::info('transfer2');
//测试不检查
if(config('wechat.payment.debug')){
return true;
}
$app_id = config('wechat.official_account.new.app_id');
$result = $this->transferV2($app_id, $trade_no, $openid, $amount, $desc);
return $result;
}
public function transferV2($app_id, $trade_no, $openid, $amount, $desc)
{
try {
$config = config('wechat.payment');
$config['app_id'] = $app_id;
$app = Factory::payment($config);
$arr = [
'partner_trade_no' => $trade_no, // 商户订单号,需保持唯一性(只能是字母或者数字,不能包含有符号)
'openid' => $openid,
'check_name' => 'NO_CHECK', // NO_CHECK不校验真实姓名, FORCE_CHECK强校验真实姓名
// 're_user_name' => '王小帅', // 如果 check_name 设置为FORCE_CHECK则必填用户真实姓名
'amount' => $amount, // 企业付款金额,单位为分
'desc' => $desc, // 企业付款操作说明信息。必填
];
$result = $app->transfer->toBalance($arr);
if($result['return_code'] == 'SUCCESS' && $result['result_code'] == 'SUCCESS'){
return null;
}else{
\Log::info($trade_no.'订单转账错误, 错误返回码'.json_encode($result));
// $this->sms->sentMessage('15872844805', $trade_no.'订单转账错误, 错误原因');
return $result;
}
} catch (Exception $e) {
$this->sms->sentMessage('15872844805', $trade_no.'订单转账错误');
\Log::debug($trade_no.'订单转账错误:'.$e->getMessage());
return ["msg"=>$e->getMessage(), "err_code_des"=>$e->getMessage()];
}
}
//企业付款到个人银行卡 公众号
public function bankTransfer($trade_no,$bank_no,$enc_true_name, $bank_code,$amount,$desc)
{
//\Log::info('transferBank');
//测试不检查
// if(config('wechat.payment.debug')){
// return true;
// }
$app_id = config('wechat.official_account.new.app_id');
$result = $this->officialBankTransfer($app_id, $trade_no,$bank_no,$enc_true_name,$bank_code,$amount, $desc);
return $result;
}
public function officialBankTransfer($app_id, $trade_no,$bank_no,$enc_true_name,$bank_code, $amount, $desc)
{
try {
$config = config('wechat.payment');
$config['app_id'] = $app_id;
$app = Factory::payment($config);
$arr = [
'partner_trade_no' => $trade_no, // 商户订单号,需保持唯一性(只能是字母或者数字,不能包含有符号)
'enc_bank_no' => $bank_no, //银行卡号
'enc_true_name'=>$enc_true_name, //银行卡对应的用户真实姓名
'bank_code' => $bank_code, // 银行编号 例1001
'amount' => $amount, // 付款金额RMB分支付总额不含手续费
'desc' => $desc, // 付款到银行卡付款说明,即订单备注 非必填
];
$result = $app->transfer->toBankCard($arr);
if($result['return_code'] == 'SUCCESS' && $result['result_code'] == 'SUCCESS'){
return null;
}else{
\Log::info($trade_no.'订单转账错误, 错误返回码'.json_encode($result));
$this->sms->sentMessage('15872844805', $trade_no.'订单转账错误, 错误原因');
return $result;
}
} catch (Exception $e) {
$this->sms->sentMessage('15872844805', $trade_no.'订单转账错误');
\Log::debug($trade_no.'订单转账错误:'.$e->getMessage());
$this->getError($e);
// return $result;
}
}
//查询企业付款到个人银行卡 公众号
public function queryBankCardOrder($trade_no)
{
//\Log::info('transferBank');
//测试不检查
// if(config('wechat.payment.debug')){
// return true;
// }
$app_id = config('wechat.official_account.new.app_id');
$result = $this->queryBankOrder($app_id, $trade_no);
return $result;
}
//查询企业付款到个人银行卡 公众号
public function queryBankOrder($app_id,$partner_trade_no)
{
try {
$config = config('wechat.payment');
$config['app_id'] = $app_id;
$app = Factory::payment($config);
$result = $app->transfer->queryBankCardOrder($partner_trade_no);
dd($result);
if($result['return_code'] == 'SUCCESS' && $result['result_code'] == 'SUCCESS'){
return null;
}else{
//\Log::info($partner_trade_no.'订单转账错误, 错误返回码'.json_encode($result));
// $this->sms->sentMessage('15872844805', $trade_no.'订单转账错误, 错误原因');
return $result;
}
} catch (Exception $e) {
// $this->sms->sentMessage('18171893605', $trade_no.'订单转账错误');
// \Log::debug($trade_no.'订单转账错误:'.$e->getMessage());
$this->getError($e);
// return $result;
}
}
public function transferred($trade_no)
{
$app_id = config('wechat.mini_program.app_id');
$result = $this->subTransferred($app_id, $trade_no);
return $result;
}
public function officialTransferred($trade_no)
{
$app_id = config('wechat.official_account.new.app_id');
$result = $this->subTransferred($app_id, $trade_no);
return $result;
}
public function subTransferred($app_id, $trade_no)
{
try {
$config = config('wechat.payment');
$config['app_id'] = $app_id;
$app = Factory::payment($config);
$result = $app->transfer->queryBalanceOrder($trade_no);
// \Log::info('result: '. json_encode($result));
if($result['return_code'] == 'SUCCESS' && $result['result_code'] == 'SUCCESS'){
return true;
}else{
\Log::info($trade_no.'订单检查转账错误, 错误返回码'.json_encode($result));
// $this->sms->sentMessage('15872844805', $trade_no.'订单检查转账错误, 错误原因'.$result['return_msg'].'业务结果'.$result['result_code']);
return false;
}
} catch (Exception $e) {
$this->sms->sentMessage('15872844805', $trade_no.'查询订单订单转账错误');
\Log::debug($trade_no.'订单检查转账错误:'.$e->getMessage());
return false;
}
}
//查询订单支付成功?
public function orderPaid($orderid){
//测试不检查
if(config('wechat.payment.debug')){
return true;
}
try{
$order = LoveOrder::where('trade_no', $orderid)->first();
$tourist_order = TouristOrder::where('trade_no', $orderid)->first();
if ((isset($order->pay_type) && $order->pay_type== 'wechat') || (isset($tourist_order->pay_type) && $tourist_order->pay_type == 'wechat')) {//app支付
$love_config = config('wechat.payment');
$love_config['app_id'] = config('wechat.love_app_id');
$payment = Factory::payment($love_config);
$rs = $payment->order->queryByOutTradeNumber($orderid);
//\Log::info($rs);
if ($rs['return_code'] == 'FAIL' || $rs['result_code'] == 'FAIL') {
//旧版本用友福同享
$ufutx_config = config('wechat.ufutx_payment');
$ufutx_config['app_id'] = config('wechat.love_app_id');
$payment = Factory::payment($ufutx_config);
$rs = $payment->order->queryByOutTradeNumber($orderid);
}
}else{
$config = config('wechat.payment');
$config['app_id'] = config('wechat.mini_program.app_id');
$payment = Factory::payment($config);
$rs = $payment->order->queryByOutTradeNumber($orderid);
}
if($rs['return_code'] == 'SUCCESS' && $rs['result_code'] == 'SUCCESS'){
if($rs['trade_state'] == 'SUCCESS'){
return true;
}else{
\Log::debug($orderid.'交易状态:'.$rs['trade_state']);
return false;
}
}else{
\Log::debug($orderid.'业务状态:'.$rs['err_code'].$rs['err_code_des']);
return false;
}
}catch(\Exception $e){
//abort(505, $orderid.'订单查询异常:'.$e->getMessage());
\Log::debug($orderid.'订单查询异常:'.$e->getMessage());
return false;
}
}
/**
* 服务端查询H5订单支付是否成功
*/
public function serverH5OrderPaid($order_id){
//测试不检查
if(config('wechat.payment.debug')){
return true;
}
try{
$order = TouristOrder::where('trade_no', $order_id)->first();
$love_config = config('wechat.payment');
$love_config['app_id'] = config('wechat.official_account.new.app_id');
$payment = Factory::payment($love_config);
$rs = $payment->order->queryByOutTradeNumber($order_id);
//\Log::info($rs);
if($rs['return_code'] == 'SUCCESS' && $rs['result_code'] == 'SUCCESS'){
if($rs['trade_state'] == 'SUCCESS'){
return true;
}else{
\Log::debug($order_id.'交易状态:'.$rs['trade_state']);
return false;
}
}else{
\Log::debug($order_id.'业务状态:'.$rs['err_code'].$rs['err_code_des']);
return false;
}
}catch(\Exception $e){
//abort(505, $orderid.'订单查询异常:'.$e->getMessage());
\Log::debug($order_id.'订单查询异常:'.$e->getMessage());
return false;
}
}
//查询h5订单支付成功?
public function officialOrderPaid($orderid){
//测试不检查
if(config('wechat.payment.debug')){
return true;
}
try{
$order = LoveOrder::where('trade_no', $orderid)->first();
if ($order->pay_type == 'h5') {//h5支付
$love_config = config('wechat.payment');
$love_config['app_id'] = config('wechat.official_account.new.app_id');
$payment = Factory::payment($love_config);
$rs = $payment->order->queryByOutTradeNumber($orderid);
//\Log::info($rs);
}
if($rs['return_code'] == 'SUCCESS' && $rs['result_code'] == 'SUCCESS'){
if($rs['trade_state'] == 'SUCCESS'){
return true;
}else{
\Log::debug($orderid.'交易状态:'.$rs['trade_state']);
return false;
}
}else{
\Log::debug($orderid.'业务状态:'.$rs['err_code'].$rs['err_code_des']);
return false;
}
}catch(\Exception $e){
//abort(505, $orderid.'订单查询异常:'.$e->getMessage());
\Log::debug($orderid.'订单查询异常:'.$e->getMessage());
return false;
}
}
/**
* 退款订单查询
* @param string $refund_trade_no 退款订单号
* @return bool
*/
public function orderRefunded($refund_trade_no)
{
if(config('wechat.payment.debug')){
return true;
}
try{
$config = config('wechat.payment');
$config['app_id'] = config('wechat.mini_program.app_id');
$payment = Factory::payment($config);
$rs = $payment->refund->queryByOutRefundNumber($refund_trade_no);
if($rs['return_code'] == 'SUCCESS' && $rs['result_code'] == 'SUCCESS'){
return true;
}else{
\Log::debug($refund_trade_no.'业务状态:'.$rs['err_code'].$rs['err_code_des']);
$this->sms->sentMessage('15872844805', $refund_trade_no.'订单查询退款异常, 错误返回码'.$rs['err_code']);
return false;
}
}catch(\Exception $e){
//abort(505, $orderid.'订单查询异常:'.$e->getMessage());
\Log::debug($refund_trade_no.'订单查询退款异常:'.$e->getMessage());
$this->sms->sentMessage('15872844805', $refund_trade_no.'订单查询退款异常');
return false;
}
}
/**
* 订单退款
* @param string $trade_no 原订单号
* @param string $refund_trade_no 退款订单号
* @param int $total_fee 总金额(分)
* @param int $refund_fee 退款金额(分)
* @param array $array 其他参数
* @return bool 是否成功
*/
public function orderRefund($trade_no, $refund_trade_no, $total_fee, $refund_fee, $array=[])
{
if(config('wechat.payment.debug')){
return true;
}
try {
$array['notify_url'] = env('APP_URL').'/api/admin/order/refun/callback';
$config = config('wechat.payment');
$config['app_id'] = config('wechat.mini_program.app_id');
$config['notify_url'] = config('app.url').'/api/admin/order/refun/callback';
$payment = Factory::payment($config);
$total_fee = (int)number_format($total_fee, 2, '', '');
$refund_fee = (int)number_format($refund_fee, 2, '', '');
Log::info("退款信息:");
Log::info($trade_no);
Log::info($refund_trade_no);
Log::info($total_fee);
Log::info($refund_fee);
Log::info("arr",$array);
// 参数分别为:商户订单号、商户退款单号、订单金额、退款金额、其他参数
$result = $payment->refund->byOutTradeNumber($trade_no, $refund_trade_no, $total_fee, $refund_fee, $array);
if($result['return_code'] == 'SUCCESS' && $result['result_code'] == 'SUCCESS'){
return ['status'=>true,'err_msg'=>null];
}else{
\Log::info($refund_trade_no.'订单退款异常, 错误返回码'.json_encode($result));//err_code_des
$this->sms->sentMessage('15872844805', $refund_trade_no.'订单退款异常, 业务结果'.$result['err_code']);
return ['status'=>false,'err_msg'=>$result['err_code_des']];
}
} catch (Exception $e) {
$this->sms->sentMessage('15872844805', $refund_trade_no.'订单退款异常');
\Log::debug($refund_trade_no.'订单退款异常:'.$e->getMessage());
return false;
}
}
/**
* 聊天通知
*/
public function chatMessageNotice($param=[])
{
$template_id = config('wechat.tpls.chat_message_notice');
$page = 'pages/users/myMessage';
$openid = $param['openid'];
$form_id = $param['form_id'];
$data = [
'keyword1'=>$param['name'],
'keyword2'=>$param['created_at'],
'keyword3'=>$param['message'],
];
return $this->send($param['openid'], $template_id, $page, $form_id, $data);
}
/**
* 等级升级通知
*/
public function rankNotice($param=[])
{
//\Log::info('测试');
$template_id = config('wechat.tpls.rank_notice');
$page = 'pages/tabBar/users/index';
$openid = $param['openid'];
$form_id = $param['form_id'];
$data = [
'keyword1'=>$param['rank_name'],
'keyword2'=>'终身会员',
'keyword3'=>$param['privilege'],
];
return $this->send($param['openid'], $template_id, $page, $form_id, $data);
}
/**
* 访问通知
*/
public function visitNotice($param=[])
{
$template_id = config('wechat.tpls.visit_notice');
$page = 'pages/home/information?id='.$param['user_id'];
$form_id = $param['form_id'];
$data = [
'keyword1'=>$param['user_name'],
'keyword2'=>$param['visit_time'],
'keyword3'=>$param['message'],
];
return $this->send($param['openid'], $template_id, $page, $form_id, $data);
}
/**
* 临时会员到期通知
*/
public function VIPEndNotice($param=[])
{
$template_id = config('wechat.tpls.vip_end_notice');
$page = 'pages/tabBar/home';
$form_id = $param['form_id'];
$data = [
'keyword1'=>$param['rank_name'],
'keyword2'=>$param['time'],
'keyword3'=>$param['message'],
];
return $this->send($param['openid'], $template_id, $page, $form_id, $data);
}
/**
* 临时会员到期通知
*/
public function VIPStartNotice($param=[])
{
$template_id = config('wechat.tpls.vip_start_notice');
$page = 'pages/tabBar/user';
$form_id = $param['form_id'];
$data = [
'keyword1'=>$param['rank_name'],
'keyword2'=>$param['name'],
'keyword3'=>$param['end_time'],
];
return $this->send($param['openid'], $template_id, $page, $form_id, $data);
}
/**
* 推荐提醒
* @param array $param [description]
* @return [type] [description]
*/
public function recommendSingleNotice($param=[])
{
$template_id = config('wechat.tpls.recommend_single');
$page = 'pages/home/information?id='.$param['user_id'].'&channel='.((isset($param['channel']))?$param['channel']:'');
$form_id = $param['form_id'];
$data = [
'keyword1'=>$param['name'],
'keyword2'=>$param['time'],
'keyword3'=>$param['message'],
];
return $this->send($param['openid'], $template_id, $page, $form_id, $data);
}
/**
* 好友申请通知
* @param array $param [description]
*/
public function addFriendNotice($param=[])
{
$template_id = config('wechat.tpls.add_friend_notice');
$page = 'pages/users/friendRequest?id='.$param['user_id'];
$form_id = $param['form_id'];
$data = [
'keyword1'=>$param['name'],
'keyword2'=>$param['time'],
'keyword3'=>$param['message'],
];
return $this->send($param['openid'], $template_id, $page, $form_id, $data);
}
/**
* 好友请求处理
* @param array $param [description]
* @return [type] [description]
*/
public function dealFriendRequest($param=[])
{
$template_id = config('wechat.tpls.deal_friend_request');
$page = 'pages/home/information?id='.$param['user_id'];
$form_id = $param['form_id'];
$data = [
'keyword1'=>$param['name'],
'keyword2'=>$param['message'],
];
return $this->send($param['openid'], $template_id, $page, $form_id, $data);
}
/**
* 会员到期提醒
* @param array $param [description]
* @return [type] [description]
*/
public function vipDeadline($param=[])
{
$template_id = config('wechat.tpls.vip_deadline');
$page = 'pages/tabBar/home/indexv2';
$form_id = $param['form_id'];
$data = [
'keyword1'=>$param['rank_name'],
'keyword2'=>$param['remain_time'],
'keyword3'=>$param['deadline'],
'keyword4'=>$param['message'],
];
return $this->send($param['openid'], $template_id, $page, $form_id, $data);
}
public function agRecommendNotcie($param=[])
{
$template_id = config('wechat.tpls.ag_recommend_notice');
$path = 'pages/home/information?id='.$param['user_id'].'&channel='.((isset($param['channel']))?$param['channel']:'');;
$data = [
'first'=> $param['title'],
'keyword1'=>$param['host'],
'keyword2'=>[
'value'=>$param['user_info'],
'color'=>'#e74c3c'
],
'keyword3'=>date('Y-m-d H:i:s'),
'remark'=> $param['remark'],
];
$url = env('APP_URL')."/mobile/#/information/".$param['user_id'];
return $this->sendToMiniProgram($param['openid'], $template_id, $path, $data, $url);
}
/**
* 访客提醒
*/
public function visitNoticeV2($param=[])
{
$template_id = config('wechat.tpls.visit_notice_v2');
$path = 'pages/home/information?id='.$param['user_id'];
$data = [
'thing1'=>["value"=>$param['name']],
'time2'=>["value"=>$param['date']],
'thing9'=>["value"=>$param['from']],
];
$url = env('APP_URL')."/mobile/#/information/".$param['user_id'];
if (isset($param['openid']) && $param['openid']) {
return $this->sendToMiniProgram($param['openid'], $template_id, $path, $data, $url);
}
}
/** 受邀请后,注册成功,提示邀请者 */
public function beRecommendNotcie($user_id,$nickname,$title,$touser_openid){
$template_id = config('wechat.tpls.be_invite_succeed_notice');
$path = 'pages/home/information?id='.$user_id;
$data = [
'first'=> $title,
'keyword1'=>$nickname,
'keyword2'=>date('Y-m-d H:i:s'),
'remark'=> '感谢您的使用',
];
$url = env('APP_URL')."/mobile/#/information/".$user_id;
return $this->sendToMiniProgram($touser_openid, $template_id, $path, $data, $url);
}
/** 客服收到新消息 提示客服 */
public function remindServiceClient($user,$service){
$param['touser'] = $service->wechat ? $service->wechat->official_openid : null;
$name = $user->nickname ?: $user->name;
// $param['template_id'] = config('wechat.tpls.activity_audited_notice');
// $param['url'] = env('APP_URL').'/admin_pro/?#/platformMGT/activityMGT';
$param['data'] = [
'first' => '有用户发来了新的消息',
'keyword1' => $name, //客户姓名
'keyword2' => $user->mobile,//客户手机
'remark' => '请及时处理',
];
$this->send($param['touser'], $param['template_id'], $param['url'], $param['data'], $param['miniprogram']??null);
}
public function ShareSuccessNotice($param=[])
{
$url = env('APP_URL').'/red/packet/activity/wechat/auth';
$template_id = config('wechat.tpls.ag_recommend_notice');
$data = [
'first'=> '【集九果分百万红包】分享成功',
'keyword1'=> $param['share_user_name'],
'keyword2'=>$param['user_name'],
'remark'=> '恭喜您!获得'.$param['chance'].'次收集果子机会马上领取GO!',
];
$url = $param['url'];
return $this->sendToOfficial($param['openid'], $template_id, $data, $url);
}
public function reportStatisticNotice($param=[])
{
$template_id = 'aE8sNkjBajSdX8qcV2pwFhSNXQcCfjjKtwEXfbddVdA';
$data = [
'first'=> $param['first'],
'keyword1'=> $param['keyword1'],
'keyword2'=>$param['keyword2'],
'keyword3'=>$param['keyword3'],
'remark'=> $param['remark'],
];
$url = '';
return $this->sendToOfficial($param['openid'], $template_id, $data, $url);
}
public function activitySuccessNotice($param=[])
{
$template_id = config('wechat.tpls.activity_success_notice');
$path = 'pages/party/detail?party_id='.$param['activity_id'];
$data = [
'first'=> '活动报名通知',
'keyword1'=> $param['title'],
'keyword2'=> $param['start_time'],
'keyword3'=> $param['address'],
'remark'=> '用户'.$param['user_name'].'['.$param['user_mobile'].']报名活动成功',
];
// $url = env('APP_URL')."/mobile/#/information/".$param['activity_id'];
return $this->sendToMiniProgram($param['openid'], $template_id, $path, $data);
}
public function sendToOfficial($openid, $template_id, $data, $url='')
{
try {
$data = [
'touser' => $openid,
'template_id' => $template_id,
'url' => $url,
'data' =>$data,
];
$result = $this->official_app->template_message->send($data);
//Log::info($result);
if ($result['errcode'] == 0) {//记录模板消息发送成功
$data['status'] = 1;
$data['err_msg'] = null;
}else{
$data['status'] = 0;
$data['err_msg'] = $result['errmsg'];
}
$data['type'] = 'official';
$this->addTemplateMsgLog($data);
return $result;
} catch (\Exception $e) {
$this->getError($e);
return false;
}
}
public function sendToMiniProgram($openid, $template_id, $path, $data, $url='')
{
try {
$data = [
'touser' => $openid,
'template_id' => $template_id,
'url'=> $url,
'miniprogram' => [
'appid' => config('wechat.mini_program.app_id'),
'pagepath' => $path,
],
'data' => $data,
];
$result = $this->official_app->template_message->send($data);
//Log::info($result);
if ($result['errcode'] == 0) {//记录模板消息发送成功
$data['status'] = 1;
$data['err_msg'] = null;
}else{
$data['status'] = 0;
$data['err_msg'] = $result['errmsg'];
}
$data['type'] = 'official';
$this->addTemplateMsgLog($data);
} catch (\Exception $e) {
$this->getError($e);
return false;
}
}
/**
* 发送模板消息
*/
public function send($openid, $template_id, $page, $form_id,$data=[]){
try {
$all_data = [
'touser' => $openid,
'template_id' => $template_id,
'page' => $page,
'form_id' => $form_id,
'data' =>$data,
];
$result = $this->app->template_message->send($all_data);
//Log::info($result);
if ($result['errcode'] == 0) {//记录模板消息发送成功
$all_data['status'] = 1;
$all_data['err_msg'] = null;
}else{
$all_data['status'] = 0;
$all_data['err_msg'] = $result['errmsg'];
}
$all_data['type'] = 'mp';
$this->addTemplateMsgLog($all_data);
} catch (\Exception $e) {
$this->getError($e);
return false;
}
}
/**
* 订阅消息
*/
//活动报名成功订阅通知
public function activitySuccessSubNotice($param=[])
{
$template_id = config('wechat.sub_tpls.activity_success_notice');
$page = "pages/party/detail?party_id=".$param['activity_id'];
$data = [
'thing2'=>["value"=>$param['title']],
'thing3'=>["value"=>$param['address']],
'time4'=>["value"=>$param['start_time']],
'phrase1'=>["value"=>"已报名"],
];
return $this->subSend($param['openid'], $template_id, $page, $data);
}
/**
* 订单支付成功通知
*/
public function orderSuccessSubNotice($param=[])
{
$template_id = config('wechat.sub_tpls.order_success_notice');
$page = "pages/users/myPay";
$data = [
'thing1'=>["value"=>$param['name']],
'amount5'=>["value"=>$param['price']],
'date6'=>["value"=>$param['updated_at']],
'thing8'=>["value"=>""],
];
return $this->subSend($param['openid'], $template_id, $page, $data);
}
/**
* 签约提醒订阅消息
* @param array $param [description]
* @return [type] [description]
*/
public function signInSubNotice($param=[])
{
$template_id = config('wechat.sub_tpls.sign_in_notice');
$page = "pages/tabBar/welcome";
$data = [
'thing7' => ['value' => $param['sign_num']], // 累计签到次数
'thing6' => ['value' => $param['award']], // 待领取奖励
'time8' => ['value' => date('Y-m-d H:i:s')], // 签到时间
'thing4' => ['value' => $param['prompt']], // 温馨提示
];
return $this->subSend($param['openid'], $template_id, $page, $data);
}
/**
* 被关注订阅消息
* @param array $param [description]
* @return [type] [description]
*/
public function followedNotice($param=[])
{
$template_id = config('wechat.sub_tpls.follow_notice');
$page = "pages/home/information?id=".$param['user_id'];
$data = [
'name1' => ['value' => $param['nickname']], // 用户昵称
'time2' => ['value' => $param['time']], // 关注时间
];
return $this->subSend($param['openid'], $template_id, $page, $data);
}
public function friendRequestNotice($param=[])
{
$template_id = config('wechat.sub_tpls.add_friend_notice');
$page = "pages/users/friendRequest";
$data = [
'name3' => ['value' => $param['nickname']], // 用户昵称
'date1' => ['value' => $param['time']], // 申请时间
'thing2' => ['value' => $param['prompt']], // 提醒
];
return $this->subSend($param['openid'], $template_id, $page, $data);
}
//活动结束发送问卷调查
public function sendActivityQuestionaireSurvey($param=[])
{
$template_id = config('wechat.sub_tpls.activity_questionaire_servey_notice');
$page = "pages/users/questionnaire?type_id=".$param['activity_id'];
$data = [
'thing1' => ['value' => $param['nickname']], // 用户昵称
'thing2' => ['value' => $param['theme']], // 活动主题
'time3' => ['value' => $param['time']], // 活动时间
'thing4' => ['value' => $param['desc']], // 描述
];
return $this->subSendV2($param['openid'], $template_id, $page, $data);
}
//团约组团成功通知(发送给拼团人员)
public function sendJoinGroupNotice($param=[])
{
//\Log::info('join_group_success_notice');
$template_id = config('wechat.sub_tpls.join_group_success_notice');
// $page = "pages/users/questionnaire?type_id=".$param['type_id'];/pages/party/SpellGroupOrder
$page = "pages/party/SpellGroupData?order_id=".$param['order_id']."&history_id=".$param['history_id'];
$desc = $param['status'] == 0 ? $param['team_desc'] : $param['desc'];
$data = [
'thing1' => ['value' => $param['title']], // 拼团商品名
'amount2' => ['value' => $param['price']], // 拼团价格
'thing3' => ['value' => $param['num']], // 拼团人数
'time4' => ['value' => $param['deadline']], // 到期时间
'thing5' => ['value' => $desc], // 温馨提示
];
return $this->subSendV2($param['openid'], $template_id, $page, $data);
}
//拼团开始通知(发给团长的通知)
public function stratGroupNotice($param){
$template_id = config('wechat.sub_tpls.start_group_notice');
$page = "pages/party/SpellGroupOrder?order_id=".$param['order_id'];
$time = date('Y-m-d H:i:s');
//\Log::info('start_group_notice '.$template_id . 'openid='.$param['openid']);
$data = [
'thing1' => ['value' => $param['title']], // 拼团商品名
'time2' => ['value' => $time], // 开团时间
'thing3' => ['value' => $param['num']], // 拼团人数
'thing4' => ['value' => $param['lead_desc']], // 温馨提示
];
return $this->subSendV2($param['openid'], $template_id, $page, $data);
}
public function subSendV2($openid, $template_id, $page, $data=[])
{
try {
if (empty($openid)) return false;
$all_data = [
'template_id'=>$template_id,
'touser'=>$openid,
'page'=>$page,
'data'=>$data,
];
$app = $this->app();
$result = $app->subscribe_message->send($all_data);
//\Log::info($result);
if ($result['errcode'] == 0) {//记录模板消息发送成功
$all_data['status'] = 1;
$all_data['err_msg'] = null;
}else{
$all_data['status'] = 0;
$all_data['err_msg'] = $result['errmsg'];
}
$all_data['type'] = 'mp';
$this->addTemplateMsgLog($all_data);
return $result;
} catch (\Exception $e) {
$this->getError($e);
return false;
}
return true;
}
/**
* [matchNotice description]
* @param array $param [description]
* @return [type] [description]
*/
public function matchNotice($param=[])
{
$template_id = config('wechat.sub_tpls.match_notice');
$page = "pages/tabBar/welcome";
$data = [
'thing1' => ['value' => $param['target_name']], // 对像名称
'thing2' => ['value' => $param['match_type']], // 匹配类型
'thing3' => ['value' => $param['tips']], // 温馨提示
];
return $this->subSend($param['openid'], $template_id, $page, $data);
}
/**
* 发送处理好友请求通知
* @param array $param [description]
* @return [type] [description]
*/
public function dealFriendRequestNotice($param=[])
{
$template_id = config('wechat.sub_tpls.deal_friend_request_notice');
if(!$template_id || is_bool($param) || empty($param['user_id'])){
return false;
}
$page = "pages/home/information?id=".$param['user_id'];
$data = [
'name1' => ['value' => $param['nickname']], // 昵称
'time2' => ['value' => $param['time']], // 时间
'thing3' => ['value' => $param['prompt']], // 提醒
];
return $this->subSend($param['openid'], $template_id, $page, $data);
}
public function vistitLogNotice($param=[])
{
$template_id = config('wechat.sub_tpls.day_visit_notice');
$page = "pages/users/visitor";
$data = [
'thing1' => ['value' => $param['nickname_str']], // 访问列表
'time2' => ['value' => $param['time']], // 时间
];
return $this->subSend($param['openid'], $template_id, $page, $data);
}
public function subSend($openid, $template_id, $page, $data=[])
{
try {
if (empty($openid)) return false;
$all_data = [
'template_id'=>$template_id,
'touser'=>$openid,
'page'=>$page,
'data'=>$data,
];
$app = $this->app();
$result = $app->subscribe_message->send($all_data);
if ($result['errcode'] == 0) {//记录模板消息发送成功
$all_data['status'] = 1;
$all_data['err_msg'] = null;
}else{
$all_data['status'] = 0;
$all_data['err_msg'] = $result['errmsg'];
}
$all_data['type'] = 'mp';
$this->addTemplateMsgLog($all_data);
return $result;
} catch (\Exception $e) {
$this->getError($e);
return false;
}
return true;
}
public function addTemplateMsgLog($data)
{
$where = $data['type'] == 'mp'?['openid'=>$data['touser']]:['official_openid'=>$data['touser']];
$user_id = Wechat::where($where)->value('user_id');
$log = new TemplateMsgLog;
$log->user_id = $user_id;
$log->openid = $data['touser'];
$log->type = $data['type'];
$log->template_id = $data['template_id'];
$log->status = $data['status'];
$log->err_msg = $data['err_msg'];
$log->data = json_encode($data);
$log->save();
return true;
}
/**
* 获取关注公众号的用户列表
*/
public function getOfficialAccountsUserOpenId(){
$result = $this->official_app->user->list();
if(!empty($result) && !empty($result['data']['openid'])){
$redis = Redis::connection('big_data');
$old_user_openId_list = $redis->keys('officialAccountsUserOpenIdList:*');
if(!empty($old_user_openId_list)){
$redis->del($old_user_openId_list);
}
$user_openId_list_key = 'officialAccountsUserOpenIdList:'.date('Y-m-d H:i:s');
$redis->set($user_openId_list_key,json_encode(['data'=>$result['data']['openid']]));
return $result['data']['openid'];
}
}
/**
* 获取用户信息
* @param $openid
* @return mixed
*/
public function getOfficialAccountUser($openid)
{
$result = $this->official_app->user->get($openid);
return $result;
}
/**
* 单次分帐
* @param $transaction_id //微信支付订单号
* @param $out_trade_no //商户分账单号,即商户订单号
* @param $receivers
* @param $sub_merchant_id
*/
public function wechatShare($transaction_id,$out_trade_no,$receivers,$sub_merchant_id){
$config = config('wechat.service_payment');
$config['cert_path'] = storage_path('wechat/service-cert.pem');
$config['key_path'] = storage_path('wechat/service-key.pem');
$payment = Factory::payment($config);
$payment->setSubMerchant($sub_merchant_id);
$result = $payment->profit_sharing->share($transaction_id,$out_trade_no,$receivers);
if($result['return_code'] == 'SUCCESS' && $result['result_code'] == 'SUCCESS'){
return true;
}else{
return false;
}
}
/**
* 多次分帐 未测试 注意:每次分帐要记下分帐订单号,否则不能进行下一次分帐
* @param $transaction_id //微信支付订单号
* @param $out_trade_no //商户分账单号,即商户订单号
* @param $receivers
* @param $sub_merchant_id
*/
public function wechatMultiShare($transaction_id,$out_trade_no,$receivers,$sub_merchant_id){
$config = config('wechat.service_payment');
$config['cert_path'] = storage_path('wechat/service_cert.pem');
$config['key_path'] = storage_path('wechat/service_key.pem');
$payment = Factory::payment($config);
$payment->setSubMerchant($sub_merchant_id);
$result = $payment->profit_sharing->multiShare($transaction_id,$out_trade_no,$receivers);
if($result['return_code'] == 'SUCCESS' && $result['result_code'] == 'SUCCESS'){
return true;
}else{
return false;
}
}
/**
* 追加分帐接收方
* @param $transaction_id //微信支付订单号
* @param $out_trade_no //商户分账单号,即商户订单号
* @return array|Support\Collection|object|\Psr\Http\Message\ResponseInterface|string
* @throws EasyWeChat\Kernel\Exceptions\InvalidArgumentException
* @throws EasyWeChat\Kernel\Exceptions\InvalidConfigException
* @throws \GuzzleHttp\Exception\GuzzleException
*/
public function addReceivers($receiver,$sub_merchant_id){
$config = config('wechat.service_payment');
$payment = Factory::payment($config);
$payment->setSubMerchant($sub_merchant_id);
$result = $payment->profit_sharing->addReceiver($receiver);
if($result['return_code'] == 'SUCCESS' && $result['result_code'] == 'SUCCESS'){
return true;
}else{
return false;
}
}
/**
* 分帐完结 单次分帐不用此接口
* @param $transaction_id //微信支付订单号
* @param $out_trade_no //商户分账单号,即商户订单号
* @param $sub_merchant_id
*/
public function markOrderAsFinished($transaction_id,$out_trade_no,$sub_merchant_id){
$config = config('wechat.service_payment');
$config['cert_path'] = storage_path('wechat/service-cert.pem');
$config['key_path'] = storage_path('wechat/service-key.pem');
$payment = Factory::payment($config);
$payment->setSubMerchant($sub_merchant_id);
$params = [
"transaction_id" => $transaction_id,
"out_order_no" => $out_trade_no,
"description" => "分账完成"
];
$result = $payment->profit_sharing->markOrderAsFinished($params);
if($result['return_code'] == 'SUCCESS' && $result['result_code'] == 'SUCCESS'){
return true;
}else{
return false;
}
}
/**
* 分帐查询
* @param $transaction_id //微信支付订单号
* @param $out_trade_no //商户分账单号,即商户订单号
* @param $sub_merchant_id
*/
public function wechatShareQuery($transaction_id,$out_trade_no,$sub_merchant_id){
$config = config('wechat.service_payment');
$payment = Factory::payment($config);
$payment->setSubMerchant($sub_merchant_id);
$result = $payment->profit_sharing->query($transaction_id,$out_trade_no);
if($result['return_code'] == 'SUCCESS' && $result['result_code'] == 'SUCCESS'){
return true;
}else{
return false;
}
}
/**
* 商家批量转账到零钱
* @param $trade_no //商家批次单号
* @param $batch_name //批次名称
* @param $batch_remark //批次备注
* @param $total_amount //转账总金额
* @param $transfer_list //转账明细列表
*/
public function transferBatches($trade_no, $batch_name, $batch_remark, $total_amount, $transfer_list)
{
// $transfer_list = [
// [
// 'out_detail_no' => \App\Facades\CommonUtilsService::getTradeNO(),
// 'transfer_amount' => 1,
// 'transfer_remark'=>'测试转账',
// 'openid'=>'oPC_2vneOWpQbicNZQAUCxuwZ4mw',
// 'user_name'=>'',
// ]
// ]
try {
$resp = $this->instance
->chain('v3/transfer/batches')
->post(['json' => [
'appid' => config('wechat.official_account.new.app_id'),
'out_trade_no' => $trade_no,
'batch_name' => $batch_name,
'batch_remark' => $batch_remark,
'total_amount' => $total_amount,
'total_num' => count($transfer_list),
'transfer_detail_list' => $transfer_list,
'transfer_scene_id' => '',
]]);
}catch (\Exception $e) {
dd($e->getMessage());
}
}
/**
* url link
*/
public function urlLink($params)
{
$app = $this->app();
$accessToken = $app->access_token;
$token = $accessToken->getToken();
$access_token = $token['access_token'];
$url = "https://api.weixin.qq.com/wxa/generate_urllink?access_token=".$access_token;
// dd($params);
$client = new Client();
$response = $client->request('POST', $url, [
'json' => $params
]);
$res = json_decode($response->getBody(), true);
if (isset($res['errcode']) && $res['errcode'] == 0) return $res['url_link'];
throw new Exception("请求url link失败, ". $res['errmsg']);
}
/**
* 申请服务商签约商户
*/
public function applymentSub($business_code, $contact_info, $subject_info,$business_info, $settlement_info, $bank_account_info, $addition_info)
{
$instance = $this->paymentInstance();
$resp = $instance->chain('v3/applyment4sub/applyment/')
->post(['json' => [
'business_code' => $business_code,
'contact_info' => $contact_info,
'subject_info' => $subject_info,
'business_info' => $business_info,
'settlement_info' => $settlement_info,
'bank_account_info' => $bank_account_info,
'addition_info' => $addition_info,
]]);
return json_decode($resp->getBody());
}
public function applymentWithCode($code)
{
$instance = $this->paymentInstance();
$resp = $instance
->chain("v3/applyment4sub/applyment/business_code/$code")
->get();
return json_decode($resp->getBody());
}
public function applymentWithId($id)
{
$resp = $this->instance
->chain("v3/applyment4sub/applyment/applyment_id/$id")
->get();
return json_decode($resp->getBody());
}
function getEncrypt($str)
{
//$str是待加密字符串
$public_key_path = 'file://'.config('wechat.payment.cert_path'); //平台证书路径
$public_key = file_get_contents($public_key_path);
$encrypted = '';
if (openssl_public_encrypt($str, $encrypted, $public_key, OPENSSL_PKCS1_OAEP_PADDING)) {
//base64编码
$sign = base64_encode($encrypted);
} else {
throw new Exception('encrypt failed');
}
return $sign;
}
public function mediaUpload($path)
{
$media = new MediaUtil($path);
$instance = $this->paymentInstance();
$resp = $instance->chain("v3/merchant/media/upload")
->post([
"body" => $media->getStream(),
"headers" => [
"content-type" => $media->getContentType(),
]
]);
return json_decode($resp->getBody());
}
public function partnerPay($order_id, $sub_mchid, $total, $openid, $trade_no, $notify_url, $desc)
{
// $openid = "oPC_2vneOWpQbicNZQAUCxuwZ4mw";
$attributes = [
'sp_appid' => config('wechat.service_payment.app_id'),
'sp_mchid' => config('wechat.service_payment.mch_id'),
'sub_mchid' => $sub_mchid,
'description' => $desc,
'out_trade_no' => $trade_no,
'notify_url' => $notify_url,
'amount' => [
"total" => (int)number_format( $total * 100, 0,'',''),
'currency' => 'CNY'
],
'payer' => [
'sp_openid' => $openid,
]
];
$instance = $this->paymentInstance();
$resp = $instance->chain('v3/pay/partner/transactions/jsapi')
->post(['json' => $attributes]);
$res = json_decode($resp->getBody());
$prepay_id = $res->prepay_id;
$config = $this->paySign($prepay_id);
$config['prepay_id'] = $prepay_id;
$attributes['order_id'] = $order_id;
return ['config'=>$config, 'attributes'=>$attributes];
}
public function partnerOrderPaid($trade_no, $sub_mchid)
{
$sp_mchid = config('wechat.service_payment.mch_id');
$instance = $this->paymentInstance();
$resp = $instance->chain("v3/pay/partner/transactions/out-trade-no/{$trade_no}?sp_mchid={$sp_mchid}&sub_mchid={$sub_mchid}")
->get();
return json_decode($resp->getBody());
}
/**
* 支付签名
* @param $prepay_id
* @return array
*/
public function paySign($prepay_id)
{
$merchantPrivateKeyFilePath = 'file://'.config('wechat.service_payment.key_path');
$merchantPrivateKeyInstance = Rsa::from($merchantPrivateKeyFilePath);
$params = [
'appId' => config('wechat.official_account.new.app_id'),
'timestamp' => (string)Formatter::timestamp(),
'nonceStr' => Formatter::nonce(),
'package' => 'prepay_id='.$prepay_id,
];
$params += ['paySign' => Rsa::sign(
Formatter::joinedByLineFeed(...array_values($params)),
$merchantPrivateKeyInstance
), 'signType' => 'RSA'];
return $params;
}
}