mirror of
https://gitee.com/huangge1199_admin/vue-pro.git
synced 2024-12-02 04:01:52 +08:00
初始化 API 错误日志模块的代码
This commit is contained in:
parent
9034da6641
commit
19a461b3cf
@ -68,20 +68,20 @@ public class ApiAccessLogFilter extends OncePerRequestFilter {
|
|||||||
|
|
||||||
private void createApiAccessLog(HttpServletRequest request, Date beginTime,
|
private void createApiAccessLog(HttpServletRequest request, Date beginTime,
|
||||||
Map<String, String> queryString, String requestBody, Exception ex) {
|
Map<String, String> queryString, String requestBody, Exception ex) {
|
||||||
|
ApiAccessLogCreateDTO accessLog = new ApiAccessLogCreateDTO();
|
||||||
try {
|
try {
|
||||||
ApiAccessLogCreateDTO accessLog = this.buildApiAccessLogDTO(request, beginTime, queryString, requestBody, ex);
|
this.buildApiAccessLogDTO(accessLog, request, beginTime, queryString, requestBody, ex);
|
||||||
apiAccessLogFrameworkService.createApiAccessLogAsync(accessLog);
|
apiAccessLogFrameworkService.createApiAccessLogAsync(accessLog);
|
||||||
} catch (Exception e) {
|
} catch (Throwable th) {
|
||||||
log.error("[createApiAccessLog][url({}) 发生异常]", request.getRequestURI(), e);
|
log.error("[createApiAccessLog][url({}) log({}) 发生异常]", request.getRequestURI(), JsonUtils.toJsonString(accessLog), th);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
private ApiAccessLogCreateDTO buildApiAccessLogDTO(HttpServletRequest request, Date beginTime,
|
private void buildApiAccessLogDTO(ApiAccessLogCreateDTO accessLog, HttpServletRequest request, Date beginTime,
|
||||||
Map<String, String> queryString, String requestBody, Exception ex) {
|
Map<String, String> queryString, String requestBody, Exception ex) {
|
||||||
ApiAccessLogCreateDTO accessLog = new ApiAccessLogCreateDTO();
|
|
||||||
// 处理用户信息
|
// 处理用户信息
|
||||||
accessLog.setUserId(WebFrameworkUtils.getLoginUserId(request));
|
accessLog.setUserId(WebFrameworkUtils.getLoginUserId(request));
|
||||||
accessLog.setUserType(WebFrameworkUtils.getUsrType(request));
|
accessLog.setUserType(WebFrameworkUtils.getUesrType(request));
|
||||||
// 设置访问结果
|
// 设置访问结果
|
||||||
CommonResult<?> result = WebFrameworkUtils.getCommonResult(request);
|
CommonResult<?> result = WebFrameworkUtils.getCommonResult(request);
|
||||||
if (result != null) {
|
if (result != null) {
|
||||||
@ -107,7 +107,6 @@ public class ApiAccessLogFilter extends OncePerRequestFilter {
|
|||||||
accessLog.setBeginTime(beginTime);
|
accessLog.setBeginTime(beginTime);
|
||||||
accessLog.setEndTime(new Date());
|
accessLog.setEndTime(new Date());
|
||||||
accessLog.setDuration((int) DateUtils.diff(accessLog.getEndTime(), accessLog.getBeginTime()));
|
accessLog.setDuration((int) DateUtils.diff(accessLog.getEndTime(), accessLog.getBeginTime()));
|
||||||
return accessLog;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
|
@ -0,0 +1,21 @@
|
|||||||
|
package cn.iocoder.dashboard.framework.logger.apilog.core.service;
|
||||||
|
|
||||||
|
import cn.iocoder.dashboard.framework.logger.apilog.core.service.dto.ApiErrorLogCreateDTO;
|
||||||
|
|
||||||
|
import javax.validation.Valid;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* API 错误日志 Framework Service 接口
|
||||||
|
*
|
||||||
|
* @author 芋道源码
|
||||||
|
*/
|
||||||
|
public interface ApiErrorLogFrameworkService {
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 创建 API 错误日志
|
||||||
|
*
|
||||||
|
* @param createDTO 创建信息
|
||||||
|
*/
|
||||||
|
void createApiErrorLogAsync(@Valid ApiErrorLogCreateDTO createDTO);
|
||||||
|
|
||||||
|
}
|
@ -0,0 +1,109 @@
|
|||||||
|
package cn.iocoder.dashboard.framework.logger.apilog.core.service.dto;
|
||||||
|
|
||||||
|
import lombok.Data;
|
||||||
|
import lombok.experimental.Accessors;
|
||||||
|
|
||||||
|
import javax.validation.constraints.NotNull;
|
||||||
|
import java.io.Serializable;
|
||||||
|
import java.util.Date;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* API 错误日志创建 DTO
|
||||||
|
*
|
||||||
|
* @author 芋道源码
|
||||||
|
*/
|
||||||
|
@Data
|
||||||
|
@Accessors(chain = true)
|
||||||
|
public class ApiErrorLogCreateDTO implements Serializable {
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 链路编号
|
||||||
|
*/
|
||||||
|
private String traceId;
|
||||||
|
/**
|
||||||
|
* 账号编号
|
||||||
|
*/
|
||||||
|
private Long userId;
|
||||||
|
/**
|
||||||
|
* 用户类型
|
||||||
|
*/
|
||||||
|
private Integer userType;
|
||||||
|
/**
|
||||||
|
* 应用名
|
||||||
|
*/
|
||||||
|
@NotNull(message = "应用名不能为空")
|
||||||
|
private String applicationName;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 请求方法名
|
||||||
|
*/
|
||||||
|
@NotNull(message = "http 请求方法不能为空")
|
||||||
|
private String requestMethod;
|
||||||
|
/**
|
||||||
|
* 访问地址
|
||||||
|
*/
|
||||||
|
@NotNull(message = "访问地址不能为空")
|
||||||
|
private String requestUrl;
|
||||||
|
/**
|
||||||
|
* 请求参数
|
||||||
|
*/
|
||||||
|
@NotNull(message = "请求参数不能为空")
|
||||||
|
private String requestParams;
|
||||||
|
/**
|
||||||
|
* 用户 IP
|
||||||
|
*/
|
||||||
|
@NotNull(message = "ip 不能为空")
|
||||||
|
private String userIp;
|
||||||
|
/**
|
||||||
|
* 浏览器 UA
|
||||||
|
*/
|
||||||
|
@NotNull(message = "User-Agent 不能为空")
|
||||||
|
private String userAgent;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 异常时间
|
||||||
|
*/
|
||||||
|
@NotNull(message = "异常时间不能为空")
|
||||||
|
private Date exceptionTime;
|
||||||
|
/**
|
||||||
|
* 异常名
|
||||||
|
*/
|
||||||
|
@NotNull(message = "异常名不能为空")
|
||||||
|
private String exceptionName;
|
||||||
|
/**
|
||||||
|
* 异常发生的类全名
|
||||||
|
*/
|
||||||
|
@NotNull(message = "异常发生的类全名不能为空")
|
||||||
|
private String exceptionClassName;
|
||||||
|
/**
|
||||||
|
* 异常发生的类文件
|
||||||
|
*/
|
||||||
|
@NotNull(message = "异常发生的类文件不能为空")
|
||||||
|
private String exceptionFileName;
|
||||||
|
/**
|
||||||
|
* 异常发生的方法名
|
||||||
|
*/
|
||||||
|
@NotNull(message = "异常发生的方法名不能为空")
|
||||||
|
private String exceptionMethodName;
|
||||||
|
/**
|
||||||
|
* 异常发生的方法所在行
|
||||||
|
*/
|
||||||
|
@NotNull(message = "异常发生的方法所在行不能为空")
|
||||||
|
private Integer exceptionLineNumber;
|
||||||
|
/**
|
||||||
|
* 异常的栈轨迹异常的栈轨迹
|
||||||
|
*/
|
||||||
|
@NotNull(message = "异常的栈轨迹不能为空")
|
||||||
|
private String exceptionStackTrace;
|
||||||
|
/**
|
||||||
|
* 异常导致的根消息
|
||||||
|
*/
|
||||||
|
@NotNull(message = "异常导致的根消息不能为空")
|
||||||
|
private String exceptionRootCauseMessage;
|
||||||
|
/**
|
||||||
|
* 异常导致的消息
|
||||||
|
*/
|
||||||
|
@NotNull(message = "异常导致的消息不能为空")
|
||||||
|
private String exceptionMessage;
|
||||||
|
|
||||||
|
}
|
@ -1 +0,0 @@
|
|||||||
package cn.iocoder.dashboard.framework.logger.apilog.core.service;
|
|
@ -1,12 +1,24 @@
|
|||||||
package cn.iocoder.dashboard.framework.web.core.handler;
|
package cn.iocoder.dashboard.framework.web.core.handler;
|
||||||
|
|
||||||
|
import cn.hutool.core.exceptions.ExceptionUtil;
|
||||||
|
import cn.hutool.core.map.MapUtil;
|
||||||
|
import cn.hutool.extra.servlet.ServletUtil;
|
||||||
import cn.iocoder.dashboard.common.exception.GlobalException;
|
import cn.iocoder.dashboard.common.exception.GlobalException;
|
||||||
import cn.iocoder.dashboard.common.exception.ServiceException;
|
import cn.iocoder.dashboard.common.exception.ServiceException;
|
||||||
import cn.iocoder.dashboard.common.pojo.CommonResult;
|
import cn.iocoder.dashboard.common.pojo.CommonResult;
|
||||||
|
import cn.iocoder.dashboard.framework.logger.apilog.core.service.ApiErrorLogFrameworkService;
|
||||||
|
import cn.iocoder.dashboard.framework.logger.apilog.core.service.dto.ApiErrorLogCreateDTO;
|
||||||
import cn.iocoder.dashboard.framework.security.core.util.SecurityFrameworkUtils;
|
import cn.iocoder.dashboard.framework.security.core.util.SecurityFrameworkUtils;
|
||||||
|
import cn.iocoder.dashboard.framework.tracer.core.util.TracerUtils;
|
||||||
|
import cn.iocoder.dashboard.framework.web.core.util.WebFrameworkUtils;
|
||||||
|
import cn.iocoder.dashboard.util.json.JsonUtils;
|
||||||
|
import cn.iocoder.dashboard.util.servlet.ServletUtils;
|
||||||
import io.github.resilience4j.ratelimiter.RequestNotPermitted;
|
import io.github.resilience4j.ratelimiter.RequestNotPermitted;
|
||||||
import lombok.extern.slf4j.Slf4j;
|
import lombok.extern.slf4j.Slf4j;
|
||||||
|
import org.apache.commons.lang3.exception.ExceptionUtils;
|
||||||
|
import org.springframework.beans.factory.annotation.Value;
|
||||||
import org.springframework.security.access.AccessDeniedException;
|
import org.springframework.security.access.AccessDeniedException;
|
||||||
|
import org.springframework.util.Assert;
|
||||||
import org.springframework.validation.BindException;
|
import org.springframework.validation.BindException;
|
||||||
import org.springframework.validation.FieldError;
|
import org.springframework.validation.FieldError;
|
||||||
import org.springframework.web.HttpRequestMethodNotSupportedException;
|
import org.springframework.web.HttpRequestMethodNotSupportedException;
|
||||||
@ -17,10 +29,13 @@ import org.springframework.web.bind.annotation.RestControllerAdvice;
|
|||||||
import org.springframework.web.method.annotation.MethodArgumentTypeMismatchException;
|
import org.springframework.web.method.annotation.MethodArgumentTypeMismatchException;
|
||||||
import org.springframework.web.servlet.NoHandlerFoundException;
|
import org.springframework.web.servlet.NoHandlerFoundException;
|
||||||
|
|
||||||
|
import javax.annotation.Resource;
|
||||||
import javax.servlet.http.HttpServletRequest;
|
import javax.servlet.http.HttpServletRequest;
|
||||||
import javax.validation.ConstraintViolation;
|
import javax.validation.ConstraintViolation;
|
||||||
import javax.validation.ConstraintViolationException;
|
import javax.validation.ConstraintViolationException;
|
||||||
import javax.validation.ValidationException;
|
import javax.validation.ValidationException;
|
||||||
|
import java.util.Date;
|
||||||
|
import java.util.Map;
|
||||||
|
|
||||||
import static cn.iocoder.dashboard.common.exception.enums.GlobalErrorCodeConstants.*;
|
import static cn.iocoder.dashboard.common.exception.enums.GlobalErrorCodeConstants.*;
|
||||||
|
|
||||||
@ -33,6 +48,12 @@ import static cn.iocoder.dashboard.common.exception.enums.GlobalErrorCodeConstan
|
|||||||
@Slf4j
|
@Slf4j
|
||||||
public class GlobalExceptionHandler {
|
public class GlobalExceptionHandler {
|
||||||
|
|
||||||
|
@Value("spring.application.name")
|
||||||
|
private String applicationName;
|
||||||
|
|
||||||
|
@Resource
|
||||||
|
private ApiErrorLogFrameworkService apiErrorLogFrameworkService;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* 处理所有异常,主要是提供给 Filter 使用
|
* 处理所有异常,主要是提供给 Filter 使用
|
||||||
* 因为 Filter 不走 SpringMVC 的流程,但是我们又需要兜底处理异常,所以这里提供一个全量的异常处理过程,保持逻辑统一。
|
* 因为 Filter 不走 SpringMVC 的流程,但是我们又需要兜底处理异常,所以这里提供一个全量的异常处理过程,保持逻辑统一。
|
||||||
@ -232,57 +253,47 @@ public class GlobalExceptionHandler {
|
|||||||
return CommonResult.error(INTERNAL_SERVER_ERROR.getCode(), INTERNAL_SERVER_ERROR.getMessage());
|
return CommonResult.error(INTERNAL_SERVER_ERROR.getCode(), INTERNAL_SERVER_ERROR.getMessage());
|
||||||
}
|
}
|
||||||
|
|
||||||
// TODO 芋艿:增加异常日志
|
private void createExceptionLog(HttpServletRequest req, Throwable e) {
|
||||||
public void createExceptionLog(HttpServletRequest req, Throwable e) {
|
// 插入错误日志
|
||||||
// // 插入异常日志
|
ApiErrorLogCreateDTO errorLog = new ApiErrorLogCreateDTO();
|
||||||
// SystemExceptionLogCreateDTO exceptionLog = new SystemExceptionLogCreateDTO();
|
try {
|
||||||
// try {
|
// 初始化 errorLog
|
||||||
// // 增加异常计数 metrics TODO 暂时去掉
|
initExceptionLog(errorLog, req, e);
|
||||||
//// EXCEPTION_COUNTER.increment();
|
// 执行插入 errorLog
|
||||||
// // 初始化 exceptionLog
|
apiErrorLogFrameworkService.createApiErrorLogAsync(errorLog);
|
||||||
// initExceptionLog(exceptionLog, req, e);
|
} catch (Throwable th) {
|
||||||
// // 执行插入 exceptionLog
|
log.error("[createExceptionLog][url({}) log({}) 发生异常]", req.getRequestURI(), JsonUtils.toJsonString(errorLog), th);
|
||||||
// createExceptionLog(exceptionLog);
|
}
|
||||||
// } catch (Throwable th) {
|
|
||||||
// log.error("[createExceptionLog][插入访问日志({}) 发生异常({})", JSON.toJSONString(exceptionLog), ExceptionUtils.getRootCauseMessage(th));
|
|
||||||
// }
|
|
||||||
}
|
}
|
||||||
|
|
||||||
// // TODO 优化点:后续可以增加事件
|
private void initExceptionLog(ApiErrorLogCreateDTO errorLog, HttpServletRequest request, Throwable e) {
|
||||||
// @Async
|
// 处理用户信息
|
||||||
// public void createExceptionLog(SystemExceptionLogCreateDTO exceptionLog) {
|
errorLog.setUserId(WebFrameworkUtils.getLoginUserId(request));
|
||||||
// try {
|
errorLog.setUserType(WebFrameworkUtils.getUesrType(request));
|
||||||
// systemExceptionLogRpc.createSystemExceptionLog(exceptionLog);
|
// 设置异常字段
|
||||||
// } catch (Throwable th) {
|
errorLog.setExceptionName(e.getClass().getName());
|
||||||
// log.error("[addAccessLog][插入异常日志({}) 发生异常({})", JSON.toJSONString(exceptionLog), ExceptionUtils.getRootCauseMessage(th));
|
errorLog.setExceptionMessage(ExceptionUtil.getMessage(e));
|
||||||
// }
|
errorLog.setExceptionRootCauseMessage(ExceptionUtil.getRootCauseMessage(e));
|
||||||
// }
|
errorLog.setExceptionStackTrace(ExceptionUtils.getStackTrace(e));
|
||||||
//
|
StackTraceElement[] stackTraceElements = e.getStackTrace();
|
||||||
// private void initExceptionLog(SystemExceptionLogCreateDTO exceptionLog, HttpServletRequest request, Throwable e) {
|
Assert.notEmpty(stackTraceElements, "异常 stackTraceElements 不能为空");
|
||||||
// // 设置账号编号
|
StackTraceElement stackTraceElement = stackTraceElements[0];
|
||||||
// exceptionLog.setUserId(CommonWebUtil.getUserId(request));
|
errorLog.setExceptionClassName(stackTraceElement.getClassName());
|
||||||
// exceptionLog.setUserType(CommonWebUtil.getUserType(request));
|
errorLog.setExceptionFileName(stackTraceElement.getFileName());
|
||||||
// // 设置异常字段
|
errorLog.setExceptionMethodName(stackTraceElement.getMethodName());
|
||||||
// exceptionLog.setExceptionName(e.getClass().getName());
|
errorLog.setExceptionLineNumber(stackTraceElement.getLineNumber());
|
||||||
// exceptionLog.setExceptionMessage(ExceptionUtil.getMessage(e));
|
// 设置其它字段
|
||||||
// exceptionLog.setExceptionRootCauseMessage(ExceptionUtil.getRootCauseMessage(e));
|
errorLog.setTraceId(TracerUtils.getTraceId());
|
||||||
// exceptionLog.setExceptionStackTrace(ExceptionUtil.getStackTrace(e));
|
errorLog.setApplicationName(applicationName);
|
||||||
// StackTraceElement[] stackTraceElements = e.getStackTrace();
|
errorLog.setRequestUrl(request.getRequestURI());
|
||||||
// Assert.notEmpty(stackTraceElements, "异常 stackTraceElements 不能为空");
|
Map<String, Object> requestParams = MapUtil.<String, Object>builder()
|
||||||
// StackTraceElement stackTraceElement = stackTraceElements[0];
|
.put("query", ServletUtil.getParamMap(request))
|
||||||
// exceptionLog.setExceptionClassName(stackTraceElement.getClassName());
|
.put("body", ServletUtil.getBody(request)).build();
|
||||||
// exceptionLog.setExceptionFileName(stackTraceElement.getFileName());
|
errorLog.setRequestParams(JsonUtils.toJsonString(requestParams));
|
||||||
// exceptionLog.setExceptionMethodName(stackTraceElement.getMethodName());
|
errorLog.setRequestMethod(request.getMethod());
|
||||||
// exceptionLog.setExceptionLineNumber(stackTraceElement.getLineNumber());
|
errorLog.setUserAgent(ServletUtils.getUserAgent(request));
|
||||||
// // 设置其它字段
|
errorLog.setUserIp(ServletUtil.getClientIP(request));
|
||||||
// exceptionLog.setTraceId(MallUtils.getTraceId())
|
errorLog.setExceptionTime(new Date());
|
||||||
// .setApplicationName(applicationName)
|
}
|
||||||
// .setUri(request.getRequestURI())
|
|
||||||
// .setQueryString(HttpUtil.buildQueryString(request))
|
|
||||||
// .setMethod(request.getMethod())
|
|
||||||
// .setUserAgent(HttpUtil.getUserAgent(request))
|
|
||||||
// .setIp(HttpUtil.getIp(request))
|
|
||||||
// .setExceptionTime(new Date());
|
|
||||||
// }
|
|
||||||
|
|
||||||
}
|
}
|
||||||
|
@ -31,7 +31,7 @@ public class WebFrameworkUtils {
|
|||||||
return (Long) request.getAttribute(REQUEST_ATTRIBUTE_LOGIN_USER_ID);
|
return (Long) request.getAttribute(REQUEST_ATTRIBUTE_LOGIN_USER_ID);
|
||||||
}
|
}
|
||||||
|
|
||||||
public static Integer getUsrType(HttpServletRequest request) {
|
public static Integer getUesrType(HttpServletRequest request) {
|
||||||
return UserTypeEnum.ADMIN.getValue(); // TODO 芋艿:等后续优化
|
return UserTypeEnum.ADMIN.getValue(); // TODO 芋艿:等后续优化
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -51,6 +51,8 @@ public class InfApiAccessLogDO extends BaseDO {
|
|||||||
*/
|
*/
|
||||||
private String applicationName;
|
private String applicationName;
|
||||||
|
|
||||||
|
// ========== 请求相关字段 ==========
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* 请求方法名
|
* 请求方法名
|
||||||
*/
|
*/
|
||||||
@ -75,6 +77,8 @@ public class InfApiAccessLogDO extends BaseDO {
|
|||||||
*/
|
*/
|
||||||
private String userAgent;
|
private String userAgent;
|
||||||
|
|
||||||
|
// ========== 执行相关字段 ==========
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* 开始请求时间
|
* 开始请求时间
|
||||||
*/
|
*/
|
||||||
|
@ -1,4 +1,152 @@
|
|||||||
package cn.iocoder.dashboard.modules.infra.dal.dataobject.logger;
|
package cn.iocoder.dashboard.modules.infra.dal.dataobject.logger;
|
||||||
|
|
||||||
public class InfApiErrorLogDO {
|
import cn.iocoder.dashboard.common.enums.UserTypeEnum;
|
||||||
|
import cn.iocoder.dashboard.framework.mybatis.core.dataobject.BaseDO;
|
||||||
|
import cn.iocoder.dashboard.modules.infra.enums.logger.ApiErrorLogProcessStatusEnum;
|
||||||
|
import com.baomidou.mybatisplus.annotation.TableName;
|
||||||
|
import lombok.*;
|
||||||
|
|
||||||
|
import java.util.Date;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* API 异常数据
|
||||||
|
*
|
||||||
|
* @author 芋道源码
|
||||||
|
*/
|
||||||
|
@TableName("inf_api_error_log")
|
||||||
|
@Data
|
||||||
|
@EqualsAndHashCode(callSuper = true)
|
||||||
|
@ToString(callSuper = true)
|
||||||
|
@Builder
|
||||||
|
@NoArgsConstructor
|
||||||
|
@AllArgsConstructor
|
||||||
|
public class InfApiErrorLogDO extends BaseDO {
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 编号
|
||||||
|
*/
|
||||||
|
private Integer id;
|
||||||
|
/**
|
||||||
|
* 用户编号
|
||||||
|
*/
|
||||||
|
private Integer userId;
|
||||||
|
/**
|
||||||
|
* 链路追踪编号
|
||||||
|
*
|
||||||
|
* 一般来说,通过链路追踪编号,可以将访问日志,错误日志,链路追踪日志,logger 打印日志等,结合在一起,从而进行排错。
|
||||||
|
*/
|
||||||
|
private String traceId;
|
||||||
|
/**
|
||||||
|
* 用户类型
|
||||||
|
*
|
||||||
|
* 枚举 {@link UserTypeEnum}
|
||||||
|
*/
|
||||||
|
private Integer userType;
|
||||||
|
/**
|
||||||
|
* 应用名
|
||||||
|
*
|
||||||
|
* 目前读取 spring.application.name
|
||||||
|
*/
|
||||||
|
private String applicationName;
|
||||||
|
|
||||||
|
// ========== 请求相关字段 ==========
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 请求方法名
|
||||||
|
*/
|
||||||
|
private String requestMethod;
|
||||||
|
/**
|
||||||
|
* 访问地址
|
||||||
|
*/
|
||||||
|
private String requestUrl;
|
||||||
|
/**
|
||||||
|
* 请求参数
|
||||||
|
*
|
||||||
|
* query: Query String
|
||||||
|
* body: Quest Body
|
||||||
|
*/
|
||||||
|
private String requestParams;
|
||||||
|
/**
|
||||||
|
* 用户 IP
|
||||||
|
*/
|
||||||
|
private String userIp;
|
||||||
|
/**
|
||||||
|
* 浏览器 UA
|
||||||
|
*/
|
||||||
|
private String userAgent;
|
||||||
|
|
||||||
|
// ========== 异常相关字段 ==========
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 异常发生时间
|
||||||
|
*/
|
||||||
|
private Date exceptionTime;
|
||||||
|
/**
|
||||||
|
* 异常名
|
||||||
|
*
|
||||||
|
* {@link Throwable#getClass()} 的类全名
|
||||||
|
*/
|
||||||
|
private String exceptionName;
|
||||||
|
/**
|
||||||
|
* 异常导致的消息
|
||||||
|
*
|
||||||
|
* {@link cn.hutool.core.exceptions.ExceptionUtil#getMessage(Throwable)}
|
||||||
|
*/
|
||||||
|
private String exceptionMessage;
|
||||||
|
/**
|
||||||
|
* 异常导致的根消息
|
||||||
|
*
|
||||||
|
* {@link cn.hutool.core.exceptions.ExceptionUtil#getRootCauseMessage(Throwable)}
|
||||||
|
*/
|
||||||
|
private String exceptionRootCauseMessage;
|
||||||
|
/**
|
||||||
|
* 异常的栈轨迹
|
||||||
|
*
|
||||||
|
* {@link org.apache.commons.lang3.exception.ExceptionUtils#getStackTrace(Throwable)}
|
||||||
|
*/
|
||||||
|
private String exceptionStackTrace;
|
||||||
|
/**
|
||||||
|
* 异常发生的类全名
|
||||||
|
*
|
||||||
|
* {@link StackTraceElement#getClassName()}
|
||||||
|
*/
|
||||||
|
private String exceptionClassName;
|
||||||
|
/**
|
||||||
|
* 异常发生的类文件
|
||||||
|
*
|
||||||
|
* {@link StackTraceElement#getFileName()}
|
||||||
|
*/
|
||||||
|
private String exceptionFileName;
|
||||||
|
/**
|
||||||
|
* 异常发生的方法名
|
||||||
|
*
|
||||||
|
* {@link StackTraceElement#getMethodName()}
|
||||||
|
*/
|
||||||
|
private String exceptionMethodName;
|
||||||
|
/**
|
||||||
|
* 异常发生的方法所在行
|
||||||
|
*
|
||||||
|
* {@link StackTraceElement#getLineNumber()}
|
||||||
|
*/
|
||||||
|
private Integer exceptionLineNumber;
|
||||||
|
|
||||||
|
// ========== 处理相关字段 ==========
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 处理状态
|
||||||
|
*
|
||||||
|
* 枚举 {@link ApiErrorLogProcessStatusEnum}
|
||||||
|
*/
|
||||||
|
private Integer processStatus;
|
||||||
|
/**
|
||||||
|
* 处理时间
|
||||||
|
*/
|
||||||
|
private Date processTime;
|
||||||
|
/**
|
||||||
|
* 处理管理员编号
|
||||||
|
*
|
||||||
|
* 关联 {@link}
|
||||||
|
*/
|
||||||
|
private Integer processUserId;
|
||||||
|
|
||||||
}
|
}
|
||||||
|
@ -0,0 +1,28 @@
|
|||||||
|
package cn.iocoder.dashboard.modules.infra.enums.logger;
|
||||||
|
|
||||||
|
import lombok.AllArgsConstructor;
|
||||||
|
import lombok.Getter;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* API 异常数据的处理状态
|
||||||
|
*
|
||||||
|
* @author 芋道源码
|
||||||
|
*/
|
||||||
|
@AllArgsConstructor
|
||||||
|
@Getter
|
||||||
|
public enum ApiErrorLogProcessStatusEnum {
|
||||||
|
|
||||||
|
INIT(0, "未处理"),
|
||||||
|
DONE(1, "已处理"),
|
||||||
|
IGNORE(2, "已忽略");
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 状态
|
||||||
|
*/
|
||||||
|
private final Integer status;
|
||||||
|
/**
|
||||||
|
* 资源类型名
|
||||||
|
*/
|
||||||
|
private final String name;
|
||||||
|
|
||||||
|
}
|
@ -0,0 +1,12 @@
|
|||||||
|
package cn.iocoder.dashboard.modules.infra.service.logger;
|
||||||
|
|
||||||
|
import cn.iocoder.dashboard.framework.logger.apilog.core.service.ApiErrorLogFrameworkService;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* API 错误日志 Service 接口
|
||||||
|
*
|
||||||
|
* @author 芋道源码
|
||||||
|
*/
|
||||||
|
public interface InfApiErrorLogService extends ApiErrorLogFrameworkService {
|
||||||
|
|
||||||
|
}
|
@ -30,7 +30,7 @@ public class InfApiAccessLogServiceImpl implements InfApiAccessLogService {
|
|||||||
|
|
||||||
@Override
|
@Override
|
||||||
@Async
|
@Async
|
||||||
public void createApiAccessLogAsync(@Valid ApiAccessLogCreateDTO createDTO) {
|
public void createApiAccessLogAsync(ApiAccessLogCreateDTO createDTO) {
|
||||||
// 插入
|
// 插入
|
||||||
InfApiAccessLogDO apiAccessLog = InfApiAccessLogConvert.INSTANCE.convert(createDTO);
|
InfApiAccessLogDO apiAccessLog = InfApiAccessLogConvert.INSTANCE.convert(createDTO);
|
||||||
apiAccessLogMapper.insert(apiAccessLog);
|
apiAccessLogMapper.insert(apiAccessLog);
|
||||||
|
@ -0,0 +1,24 @@
|
|||||||
|
package cn.iocoder.dashboard.modules.infra.service.logger.impl;
|
||||||
|
|
||||||
|
import cn.iocoder.dashboard.framework.logger.apilog.core.service.dto.ApiErrorLogCreateDTO;
|
||||||
|
import cn.iocoder.dashboard.modules.infra.service.logger.InfApiErrorLogService;
|
||||||
|
import org.springframework.scheduling.annotation.Async;
|
||||||
|
import org.springframework.stereotype.Service;
|
||||||
|
import org.springframework.validation.annotation.Validated;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* API 错误日志 Service 实现类
|
||||||
|
*
|
||||||
|
* @author 芋道源码
|
||||||
|
*/
|
||||||
|
@Service
|
||||||
|
@Validated
|
||||||
|
public class InfApiErrorLogServiceImpl implements InfApiErrorLogService {
|
||||||
|
|
||||||
|
@Override
|
||||||
|
@Async
|
||||||
|
public void createApiErrorLogAsync(ApiErrorLogCreateDTO createDTO) {
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
Loading…
Reference in New Issue
Block a user