From a919f029e2fd5b82c2c36c0d50dfa3e7bb2356f0 Mon Sep 17 00:00:00 2001 From: leekay0218 <272112456@qq.com> Date: Thu, 31 Mar 2022 19:45:03 +0800 Subject: [PATCH] =?UTF-8?q?=E3=80=90=E7=A8=8B=E5=BA=8F=E7=9B=AE=E5=BD=95?= =?UTF-8?q?=E3=80=91=E4=BF=AE=E6=94=B9=E4=BA=86=E6=97=A5=E5=BF=97=E6=A0=BC?= =?UTF-8?q?=E5=BC=8F=EF=BC=8C=E5=A2=9E=E5=8A=A0=E4=BA=86=E6=97=A5=E5=BF=97?= =?UTF-8?q?=E9=85=8D=E7=BD=AE=EF=BC=8C=E5=A2=9E=E5=8A=A0=E4=BA=86=E5=85=AC?= =?UTF-8?q?=E5=85=B1=E4=B8=AD=E9=97=B4=E4=BB=B6=EF=BC=8C=E5=A2=9E=E5=8A=A0?= =?UTF-8?q?=E4=BA=86=E4=B8=9A=E5=8A=A1=E6=88=90=E5=8A=9F=E5=92=8C=E5=A4=B1?= =?UTF-8?q?=E8=B4=A5=E7=9A=84=E6=97=A5=E5=BF=97=EF=BC=8C=E5=A2=9E=E5=8A=A0?= =?UTF-8?q?=E4=BA=86http=E5=93=8D=E5=BA=94=E4=BA=8B=E4=BB=B6=E7=9B=91?= =?UTF-8?q?=E5=90=AC=E3=80=82?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .../app/adminapi/AdminApiExceptionHandle.php | 33 +++++++--- crmeb/app/api/ApiExceptionHandle.php | 33 +++++++--- crmeb/app/event.php | 2 +- crmeb/app/http/middleware/BaseMiddleware.php | 38 +++++++++++ crmeb/app/kefuapi/KefuApiExceptionHandle.php | 33 +++++++--- crmeb/app/listener/http/HttpEnd.php | 63 +++++++++++++++++++ crmeb/app/middleware.php | 6 +- crmeb/config/log.php | 25 +++++--- 8 files changed, 196 insertions(+), 37 deletions(-) create mode 100644 crmeb/app/http/middleware/BaseMiddleware.php create mode 100644 crmeb/app/listener/http/HttpEnd.php diff --git a/crmeb/app/adminapi/AdminApiExceptionHandle.php b/crmeb/app/adminapi/AdminApiExceptionHandle.php index 3cbc9e423..a70794c7b 100644 --- a/crmeb/app/adminapi/AdminApiExceptionHandle.php +++ b/crmeb/app/adminapi/AdminApiExceptionHandle.php @@ -19,6 +19,7 @@ use think\exception\DbException; use think\exception\Handle; use think\exception\ValidateException; use think\facade\Env; +use think\facade\Log; use think\Response; use Throwable; @@ -27,26 +28,42 @@ class AdminApiExceptionHandle extends Handle /** * 记录异常信息(包括日志或者其它方式记录) - * * @access public * @param Throwable $exception * @return void */ - public function report(Throwable $exception): void + public function report(Throwable $exception):void { - // 使用内置的方式记录异常日志 - parent::report($exception); + $data = [ + 'file' => $exception->getFile(), + 'line' => $exception->getLine(), + 'message' => $this->getMessage($exception), + 'code' => $this->getCode($exception), + ]; + + //日志内容 + $log = [ + request()->adminId(), //管理员ID + request()->ip(), //客户ip + ceil(msectime() - (request()->time(true) * 1000)), //耗时(毫秒) + request()->rule()->getMethod(), //请求类型 + str_replace("/", "", request()->rootUrl()), //应用 + request()->baseUrl(), //路由 + json_encode(request()->param(), JSON_UNESCAPED_UNICODE | JSON_UNESCAPED_SLASHES), //请求参数 + json_encode($data, JSON_UNESCAPED_UNICODE | JSON_UNESCAPED_SLASHES), //报错数据 + + ]; + Log::write(implode("|", $log), "error"); } /** * Render an exception into an HTTP response. - * * @access public * @param \think\Request $request - * @param Throwable $e + * @param Throwable $e * @return Response */ - public function render($request, Throwable $e): Response + public function render($request, Throwable $e):Response { $massageData = Env::get('app_debug', false) ? [ 'file' => $e->getFile(), @@ -58,7 +75,7 @@ class AdminApiExceptionHandle extends Handle if ($e instanceof DbException) { return app('json')->fail('数据获取失败', $massageData); } elseif ($e instanceof AuthException || $e instanceof ValidateException || $e instanceof ApiException) { - return app('json')->make($e->getCode() ?: 400, $e->getMessage()); + return app('json')->make($e->getCode() ? : 400, $e->getMessage()); } elseif ($e instanceof AdminException) { return app('json')->fail($e->getMessage(), $massageData); } else { diff --git a/crmeb/app/api/ApiExceptionHandle.php b/crmeb/app/api/ApiExceptionHandle.php index 18f872412..034199da0 100644 --- a/crmeb/app/api/ApiExceptionHandle.php +++ b/crmeb/app/api/ApiExceptionHandle.php @@ -17,6 +17,7 @@ use crmeb\exceptions\AuthException; use think\exception\DbException; use think\exception\Handle; use think\facade\Env; +use think\facade\Log; use think\Response; use Throwable; use think\exception\ValidateException; @@ -26,26 +27,42 @@ class ApiExceptionHandle extends Handle /** * 记录异常信息(包括日志或者其它方式记录) - * * @access public * @param Throwable $exception * @return void */ - public function report(Throwable $exception): void + public function report(Throwable $exception):void { - // 使用内置的方式记录异常日志 - parent::report($exception); + $data = [ + 'file' => $exception->getFile(), + 'line' => $exception->getLine(), + 'message' => $this->getMessage($exception), + 'code' => $this->getCode($exception), + ]; + + //日志内容 + $log = [ + request()->uid(), //用户ID + request()->ip(), //客户ip + ceil(msectime() - (request()->time(true) * 1000)), //耗时(毫秒) + request()->rule()->getMethod(), //请求类型 + str_replace("/", "", request()->rootUrl()), //应用 + request()->baseUrl(), //路由 + json_encode(request()->param(), JSON_UNESCAPED_UNICODE | JSON_UNESCAPED_SLASHES), //请求参数 + json_encode($data, JSON_UNESCAPED_UNICODE | JSON_UNESCAPED_SLASHES), //报错数据 + + ]; + Log::write(implode("|", $log), "error"); } /** * Render an exception into an HTTP response. - * * @access public * @param \think\Request $request - * @param Throwable $e + * @param Throwable $e * @return Response */ - public function render($request, Throwable $e): Response + public function render($request, Throwable $e):Response { // 添加自定义异常处理机制 if ($e instanceof DbException) { @@ -54,7 +71,7 @@ class ApiExceptionHandle extends Handle 'message' => $e->getMessage(), 'line' => $e->getLine(), ]); - } else if ($e instanceof AuthException || $e instanceof ApiException || $e instanceof ValidateException) { + } elseif ($e instanceof AuthException || $e instanceof ApiException || $e instanceof ValidateException) { return app('json')->fail($e->getMessage()); } else { return app('json')->fail('很抱歉!系统开小差了', Env::get('app_debug', false) ? [ diff --git a/crmeb/app/event.php b/crmeb/app/event.php index a7269d79b..0a54a6687 100644 --- a/crmeb/app/event.php +++ b/crmeb/app/event.php @@ -19,7 +19,7 @@ return [ 'listen' => [ 'AppInit' => [], 'HttpRun' => [], - 'HttpEnd' => [], + 'HttpEnd' => [\app\listener\http\HttpEnd::class], 'LogLevel' => [], 'LogWrite' => [], 'StoreProductOrderDeliveryAfter' => [], // OrderSubscribe 送货 发送模板消息 admin模块 order.StoreOrder控制器/order.combinationOrder控制器 diff --git a/crmeb/app/http/middleware/BaseMiddleware.php b/crmeb/app/http/middleware/BaseMiddleware.php new file mode 100644 index 000000000..ef19d49fc --- /dev/null +++ b/crmeb/app/http/middleware/BaseMiddleware.php @@ -0,0 +1,38 @@ + +// +---------------------------------------------------------------------- + +namespace app\http\middleware; + + +use app\Request; +use crmeb\interfaces\MiddlewareInterface; + +/** + * Class BaseMiddleware + * @package app\api\middleware + */ +class BaseMiddleware implements MiddlewareInterface +{ + public function handle(Request $request, \Closure $next, bool $force = true) + { + if (!Request::hasMacro('uid')) { + Request::macro('uid', function(){ return 0; }); + } + if (!Request::hasMacro('adminId')) { + Request::macro('adminId', function(){ return 0; }); + } + if (!Request::hasMacro('kefuId')) { + Request::macro('kefuId', function(){ return 0; }); + } + + return $next($request); + } +} diff --git a/crmeb/app/kefuapi/KefuApiExceptionHandle.php b/crmeb/app/kefuapi/KefuApiExceptionHandle.php index c1c81fd40..6db923c0d 100644 --- a/crmeb/app/kefuapi/KefuApiExceptionHandle.php +++ b/crmeb/app/kefuapi/KefuApiExceptionHandle.php @@ -16,6 +16,7 @@ use crmeb\exceptions\AuthException; use think\exception\Handle; use think\exception\ValidateException; use think\facade\Config; +use think\facade\Log; use think\Response; use Throwable; @@ -23,26 +24,42 @@ class KefuApiExceptionHandle extends Handle { /** * 记录异常信息(包括日志或者其它方式记录) - * * @access public * @param Throwable $exception * @return void */ - public function report(Throwable $exception): void + public function report(Throwable $exception):void { - // 使用内置的方式记录异常日志 - parent::report($exception); + $data = [ + 'file' => $exception->getFile(), + 'line' => $exception->getLine(), + 'message' => $this->getMessage($exception), + 'code' => $this->getCode($exception), + ]; + + //日志内容 + $log = [ + request()->kefuId(), //客服ID + request()->ip(), //客户ip + ceil(msectime() - (request()->time(true) * 1000)), //耗时(毫秒) + request()->rule()->getMethod(), //请求类型 + str_replace("/", "", request()->rootUrl()), //应用 + request()->baseUrl(), //路由 + json_encode(request()->param(), JSON_UNESCAPED_UNICODE | JSON_UNESCAPED_SLASHES), //请求参数 + json_encode($data, JSON_UNESCAPED_UNICODE | JSON_UNESCAPED_SLASHES), //报错数据 + + ]; + Log::write(implode("|", $log), "error"); } /** * Render an exception into an HTTP response. - * * @access public * @param \think\Request $request - * @param Throwable $e + * @param Throwable $e * @return Response */ - public function render($request, Throwable $e): Response + public function render($request, Throwable $e):Response { $massageData = Config::get('app_debug', false) ? [ 'file' => $e->getFile(), @@ -54,7 +71,7 @@ class KefuApiExceptionHandle extends Handle if ($e instanceof DbException) { return app('json')->fail('数据获取失败', $massageData); } elseif ($e instanceof ValidateException || $e instanceof AuthException) { - return app('json')->make($e->getCode() ?: 400, $e->getMessage()); + return app('json')->make($e->getCode() ? : 400, $e->getMessage()); } else { return app('json')->code(200)->make(400, $e->getMessage(), $massageData); } diff --git a/crmeb/app/listener/http/HttpEnd.php b/crmeb/app/listener/http/HttpEnd.php new file mode 100644 index 000000000..c55f582f9 --- /dev/null +++ b/crmeb/app/listener/http/HttpEnd.php @@ -0,0 +1,63 @@ + +// +---------------------------------------------------------------------- + +namespace app\listener\http; + +use think\facade\Log; +use think\Response; + +/** + * 订单创建事件 + * Class Create + * @package app\listener\http + */ +class HttpEnd +{ + public function handle(Response $response):void + { + //业务成功和失败分开存储 + $status = isset($response->getData()["status"]) ? $response->getData()["status"] : 0; + if ($status == 200) { + //业务成功日志开关 + if (config("log.success_close")) return; + $type = "success"; + } else { + //业务失败日志开关 + if (config("log.fail_close")) return; + $type = "fail"; + } + + //当前用户身份标识 + if (!empty(request()->uid())) { + $uid = request()->uid(); + } elseif (!empty(request()->adminId())) { + $uid = request()->adminId(); + } elseif (!empty(request()->kefuId())) { + $uid = request()->kefuId(); + } else { + $uid = 0; + } + + //日志内容 + $log = [ + $uid, //用户ID + request()->ip(), //客户ip + ceil(msectime() - (request()->time(true) * 1000)), //耗时(毫秒) + request()->rule()->getMethod(), //请求类型 + str_replace("/", "", request()->rootUrl()), //应用 + request()->baseUrl(), //路由 + json_encode(request()->param(), JSON_UNESCAPED_UNICODE | JSON_UNESCAPED_SLASHES), //请求参数 + json_encode($response->getData(), JSON_UNESCAPED_UNICODE | JSON_UNESCAPED_SLASHES), //响应数据 + + ]; + Log::write(implode("|", $log), $type); + } +} diff --git a/crmeb/app/middleware.php b/crmeb/app/middleware.php index 39e1aac4d..6cf039eef 100644 --- a/crmeb/app/middleware.php +++ b/crmeb/app/middleware.php @@ -14,9 +14,11 @@ return [ // 多语言加载 // \think\middleware\LoadLangPack::class, // Session初始化 - \think\middleware\SessionInit::class, + \think\middleware\SessionInit::class, //多语言初始化 - \think\middleware\LoadLangPack::class, + \think\middleware\LoadLangPack::class, // 页面Trace调试 // \think\middleware\TraceDebug::class, + //初始化基础中间件 + \app\http\middleware\BaseMiddleware::class, ]; diff --git a/crmeb/config/log.php b/crmeb/config/log.php index ab1153007..a30d00ad4 100644 --- a/crmeb/config/log.php +++ b/crmeb/config/log.php @@ -15,27 +15,32 @@ use think\facade\Env; // +---------------------------------------------------------------------- return [ // 默认日志记录通道 - 'default' => Env::get('log.channel', 'file'), + 'default' => Env::get('log.channel', 'file'), // 日志记录级别 - 'level' => ['error','warning'], + 'level' => ['error', 'warning', 'fail', 'success'], // 日志类型记录的通道 ['error'=>'email',...] 'type_channel' => [], // 是否关闭日志写入 - 'close' => false, - + 'close' => false, + //是否关闭业务成功日志 + 'success_close' => false, + //是否关闭业务失败日志 + 'fail_close' => false, // 日志通道列表 - 'channels' => [ + 'channels' => [ 'file' => [ // 日志记录方式 - 'type' => 'File', + 'type' => 'File', // 日志保存目录 - 'path' => app()->getRuntimePath() . 'log' . DIRECTORY_SEPARATOR, + 'path' => app()->getRuntimePath() . 'log' . DIRECTORY_SEPARATOR, // 单文件日志写入 - 'single' => false, + 'single' => false, // 独立日志级别 - 'apart_level' => [], + 'apart_level' => ['error', 'fail', 'success'], // 最大日志文件数量 - 'max_files' => 0, + 'max_files' => 0, + 'time_format' => 'Y-m-d H:i:s', + 'format' => '%s|%s|%s' ], // 其它日志通道配置 ],