yl-backend/src/main/java/com/guwan/backend/aspect/OperationLogAspect.java

133 lines
4.8 KiB
Java
Raw Normal View History

2024-12-07 19:03:14 +08:00
package com.guwan.backend.aspect;
import com.fasterxml.jackson.databind.ObjectMapper;
import com.guwan.backend.annotation.OperationLog;
import com.guwan.backend.pojo.entity.SysLog;
2024-12-07 19:03:14 +08:00
import com.guwan.backend.mapper.SysLogMapper;
import com.guwan.backend.security.CustomUserDetails;
import jakarta.servlet.http.HttpServletRequest;
import lombok.RequiredArgsConstructor;
import lombok.extern.slf4j.Slf4j;
import org.aspectj.lang.ProceedingJoinPoint;
import org.aspectj.lang.annotation.Around;
import org.aspectj.lang.annotation.Aspect;
2024-12-07 19:15:52 +08:00
import org.aspectj.lang.annotation.Pointcut;
2024-12-07 19:03:14 +08:00
import org.aspectj.lang.reflect.MethodSignature;
import org.springframework.security.core.Authentication;
import org.springframework.security.core.context.SecurityContextHolder;
import org.springframework.stereotype.Component;
import org.springframework.web.context.request.RequestContextHolder;
import org.springframework.web.context.request.ServletRequestAttributes;
import java.lang.reflect.Method;
import java.time.LocalDateTime;
import java.util.Arrays;
@Slf4j
@Aspect
@Component
@RequiredArgsConstructor
public class OperationLogAspect {
private final SysLogMapper sysLogMapper;
2024-12-07 19:41:47 +08:00
2024-12-07 19:03:14 +08:00
private final ObjectMapper objectMapper;
2024-12-07 19:15:52 +08:00
/**
* 定义切点
*/
@Pointcut("@annotation(com.guwan.backend.annotation.OperationLog)")
public void logPointcut() {
}
/**
* 环绕通知
*/
@Around("logPointcut() && @annotation(operationLog)")
2024-12-07 19:03:14 +08:00
public Object around(ProceedingJoinPoint point, OperationLog operationLog) throws Throwable {
long beginTime = System.currentTimeMillis();
SysLog sysLog = new SysLog();
try {
Object result = point.proceed();
sysLog.setStatus(1);
return result;
} catch (Exception e) {
sysLog.setStatus(0);
sysLog.setErrorMsg(e.getMessage());
throw e;
} finally {
saveLog(point, operationLog, beginTime, sysLog);
2024-12-07 19:03:14 +08:00
}
}
2024-12-07 19:15:52 +08:00
/**
* 保存日志
*/
2024-12-07 19:03:14 +08:00
private void saveLog(ProceedingJoinPoint joinPoint, OperationLog operationLog, long beginTime, SysLog sysLog) {
2024-12-07 19:46:23 +08:00
try {
// 获取当前请求
ServletRequestAttributes attributes = (ServletRequestAttributes) RequestContextHolder.getRequestAttributes();
if (attributes != null) {
HttpServletRequest request = attributes.getRequest();
sysLog.setIp(getIpAddress(request));
sysLog.setUserAgent(request.getHeader("User-Agent"));
}
2024-12-07 19:03:14 +08:00
2024-12-07 19:46:23 +08:00
// 获取当前用户信息
Authentication authentication = SecurityContextHolder.getContext().getAuthentication();
2025-03-30 20:32:16 +08:00
//Java 16+ 模式匹配写法
2024-12-07 19:46:23 +08:00
if (authentication != null && authentication.getPrincipal() instanceof CustomUserDetails userDetails) {
sysLog.setUserId(userDetails.getUserId());
sysLog.setUsername(userDetails.getUsername());
}
2024-12-07 19:03:14 +08:00
2024-12-07 19:46:23 +08:00
// 获取方法信息
MethodSignature signature = (MethodSignature) joinPoint.getSignature();
Method method = signature.getMethod();
String className = method.getDeclaringClass().getName();
String methodName = method.getName();
sysLog.setMethod(className + "." + methodName);
2024-12-07 19:03:14 +08:00
2024-12-07 19:46:23 +08:00
// 获取请求参数
try {
String params = objectMapper.writeValueAsString(joinPoint.getArgs());
sysLog.setParams(params.length() > 2000 ? params.substring(0, 2000) : params);
} catch (Exception e) {
log.error("序列化请求参数失败", e);
sysLog.setParams(Arrays.toString(joinPoint.getArgs()));
}
2024-12-07 19:15:52 +08:00
2024-12-07 19:46:23 +08:00
// 设置操作信息
sysLog.setOperation(operationLog.description());
sysLog.setCreateTime(LocalDateTime.now());
sysLog.setTimeConsuming(System.currentTimeMillis() - beginTime);
2024-12-07 19:15:52 +08:00
2024-12-07 19:46:23 +08:00
// 保存日志
sysLogMapper.insert(sysLog);
} catch (Exception e) {
log.error("记录操作日志失败", e);
}
2024-12-07 19:03:14 +08:00
}
2024-12-07 19:15:52 +08:00
/**
* 获取IP地址
*/
2024-12-07 19:03:14 +08:00
private String getIpAddress(HttpServletRequest request) {
String ip = request.getHeader("X-Forwarded-For");
if (ip == null || ip.length() == 0 || "unknown".equalsIgnoreCase(ip)) {
ip = request.getHeader("Proxy-Client-IP");
}
if (ip == null || ip.length() == 0 || "unknown".equalsIgnoreCase(ip)) {
ip = request.getHeader("WL-Proxy-Client-IP");
}
if (ip == null || ip.length() == 0 || "unknown".equalsIgnoreCase(ip)) {
ip = request.getRemoteAddr();
}
2024-12-07 19:15:52 +08:00
// 多个代理的情况第一个IP为客户端真实IP
if (ip != null && ip.contains(",")) {
ip = ip.split(",")[0].trim();
}
2024-12-07 19:03:14 +08:00
return ip;
}
}