我是靠谱客的博主 义气保温杯,最近开发中收集的这篇文章主要介绍SpringAOP统一日志处理切面,觉得挺不错的,现在分享给大家,希望可以做个参考。

概述

通过AOP实现统一的日志管理

先放出AOP部分的代码


import cn.hutool.core.util.StrUtil;
import cn.hutool.core.util.URLUtil;
import cn.hutool.json.JSONUtil;
import cn.hutool.system.UserInfo;
import com.alibaba.fastjson.JSONObject;
import com.framework.modules.sys.dao.tbLogDao;
import com.framework.modules.sys.entity.SysUserEntity;
import io.swagger.annotations.ApiOperation;
import org.apache.shiro.SecurityUtils;
import org.aspectj.lang.JoinPoint;
import org.aspectj.lang.ProceedingJoinPoint;
import org.aspectj.lang.Signature;
import org.aspectj.lang.annotation.*;
import org.aspectj.lang.reflect.MethodSignature;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.core.annotation.Order;
import org.springframework.stereotype.Component;
import org.springframework.util.StringUtils;
import org.springframework.web.bind.annotation.RequestBody;
import org.springframework.web.bind.annotation.RequestParam;
import org.springframework.web.context.request.RequestContextHolder;
import org.springframework.web.context.request.ServletRequestAttributes;
import javax.servlet.http.HttpServletRequest;
import java.lang.reflect.Method;
import java.lang.reflect.Parameter;
import java.sql.Date;
import java.text.SimpleDateFormat;
import java.util.ArrayList;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
/**
* @author 尚先生
* 统一日志处理切面
* @date 2020/6/23 11:20
*/
@Aspect
@Component
@Order(1)
public class WebLogAspect {
private static final Logger LOGGER = LoggerFactory.getLogger(WebLogAspect.class);
//通过dao层 写入数据库 如不需要写入请注释
@Autowired
com.framework.modules.sys.dao.tbLogDao tbLogDao;
//@Pointcut 我是切面 
@Pointcut("execution(public * com.framework.modules.sys.controller.*.*(..))")
public void webLog() {
}
@Before("webLog()")
//@Before: 我是前置通知, 在方法执行之前执行 
public void doBefore(JoinPoint joinPoint) throws Throwable {
}
@AfterReturning(value = "webLog()", returning = "ret")
//@AfterRunning: 我是返回通知, 在方法返回结果之后执行
public void doAfterReturning(Object ret) throws Throwable {
}
//@After: 我是后置通知, 在方法执行之后执行 (被遗忘)
@Around("webLog()")
//@Around: 我是环绕通知, 围绕着方法执行
public Object doAround(ProceedingJoinPoint joinPoint) throws Throwable {
long startTime = System.currentTimeMillis();
SimpleDateFormat dateformat = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss");
//获取当前请求对象
ServletRequestAttributes attributes = (ServletRequestAttributes) RequestContextHolder.getRequestAttributes();
HttpServletRequest request = attributes != null ? attributes.getRequest() : null;
//记录请求信息
WebLog webLog = new WebLog();
Object result = joinPoint.proceed();
Signature signature = joinPoint.getSignature();
MethodSignature methodSignature = (MethodSignature) signature;
Method method = methodSignature.getMethod();
//请注意需要方法上有@ApiOperation 注释才能拿到方法的描述 可以自行修改
if (method.isAnnotationPresent(ApiOperation.class)) {
ApiOperation apiOperation = method.getAnnotation(ApiOperation.class);
webLog.setDescription(apiOperation.value());
}
long endTime = System.currentTimeMillis();
assert request != null;
//TODO 请注意这段代码 是从Shiro获取当前登录的用户信息 以及放入 可能为null 
SysUserEntity sysUserEntity=
(SysUserEntity) SecurityUtils.getSubject().getPrincipal();
if (sysUserEntity!=null){
webLog.setUser_id(sysUserEntity.getUserId());
webLog.setUsername(sysUserEntity.getUsername());
webLog.setReal_project(sysUserEntity.getRealname());
}
String urlStr = request.getRequestURL().toString();
webLog.setBasePath(StrUtil.removeSuffix(urlStr, URLUtil.url(urlStr).getPath()));
webLog.setIp(request.getRemoteAddr());
webLog.setMethod(request.getMethod());
webLog.setParameter(JSONObject.toJSONString(getParameter(method, joinPoint.getArgs())));
webLog.setResult(result.toString());
webLog.setSpendTime((int) (endTime - startTime));
webLog.setStartTime(dateformat.parse(dateformat.format(startTime)));
webLog.setUri(request.getRequestURI());
webLog.setUrl(request.getRequestURL().toString());
LOGGER.info("{}", JSONUtil.parse(webLog));
//这句是写入数据库如不需要 请去掉
tbLogDao.insert(webLog);
return result;
}
/**
* 根据方法和传入的参数获取请求参数
*/
private Object getParameter(Method method, Object[] args) {
List<Object> argList = new ArrayList<>();
Parameter[] parameters = method.getParameters();
for (int i = 0; i < parameters.length; i++) {
//将RequestBody注解修饰的参数作为请求参数
RequestBody requestBody = parameters[i].getAnnotation(RequestBody.class);
if (requestBody != null) {
argList.add(args[i]);
}
//将RequestParam注解修饰的参数作为请求参数
RequestParam requestParam = parameters[i].getAnnotation(RequestParam.class);
if (requestParam != null) {
Map<String, Object> map = new HashMap<>();
String key = parameters[i].getName();
if (!StringUtils.isEmpty(requestParam.value())) {
key = requestParam.value();
}
map.put(key, args[i]);
argList.add(map);
}
}
if (argList.size() == 0) {
return null;
} else if (argList.size() == 1) {
return argList.get(0);
} else {
return argList;
}
}
}

再列出WebLog 对象


import com.baomidou.mybatisplus.activerecord.Model;
import com.baomidou.mybatisplus.annotations.TableField;
import com.baomidou.mybatisplus.annotations.TableId;
import com.baomidou.mybatisplus.annotations.TableName;
import com.baomidou.mybatisplus.enums.IdType;
import lombok.Data;
import lombok.Getter;
import lombok.Setter;
import lombok.ToString;
import java.io.Serializable;
import java.util.Date;
@ToString
@TableName("tb_user_log")
@Data
public class WebLog extends Model<WebLog> {
private static final long serialVersionUID = 1L;
@TableId(value = "log_id",type = IdType.AUTO)
private Integer log_id;
/**
* 操作描述
*/
@TableField("description")
private String description;
/**
* 操作用户
*/
@TableField("username")
private String username;
/**
* 操作用户id
*/
@TableField("user_id")
private String user_id;
/**
* 真实姓名
*/
@TableField("real_project")
private String real_project;
/**
* 操作时间
*/
@TableField("startTime")
private Date startTime;
/**
* 消耗时间
*/
@TableField("spendTime")
private Integer spendTime;
/**
* 根路径
*/
@TableField("basePath")
private String basePath;
/**
* URI
*/
@TableField("uri")
private String uri;
/**
* URL
*/
@TableField("URL")
private String url;
/**
* 请求类型
*/
@TableField("method")
private String method;
/**
* IP地址
*/
@TableField("ip")
private String ip;
/**
* 请求参数
*/
@TableField("parameter")
private String parameter;
/**
* 请求返回的结果
*/
@TableField("result")
private String result;
@Override
protected Serializable pkVal() {
return this.log_id;
}
}

最后

以上就是义气保温杯为你收集整理的SpringAOP统一日志处理切面的全部内容,希望文章能够帮你解决SpringAOP统一日志处理切面所遇到的程序开发问题。

如果觉得靠谱客网站的内容还不错,欢迎将靠谱客网站推荐给程序员好友。

本图文内容来源于网友提供,作为学习参考使用,或来自网络收集整理,版权属于原作者所有。
点赞(40)

评论列表共有 0 条评论

立即
投稿
返回
顶部