1.操作日志实体类

@Document(collection = "operation_log")
@Getter
@Setter
@ToString
public class OperationLog extends BaseEntityWithId {
private String userId; // 操作人
private String resource; // 操作的资源
private String requestMethod; // 请求方式
private String beanName; // 操作的类
private String methodName; // 操作的模块
private String requestParams; // 请求的参数
private String responseData; // 返回数据
}

2.拦截器

package com.vian.admin.config;

import com.alibaba.fastjson.JSON;
import com.vian.admin.entity.OperationLog;
import com.vian.admin.event.OperationLogEvent;
import com.vian.core.configuration.event.EventPublisher;
import com.vian.microservice.security.SecurityUtils;
import lombok.extern.slf4j.Slf4j;
import org.aspectj.lang.JoinPoint;
import org.aspectj.lang.annotation.AfterReturning;
import org.aspectj.lang.annotation.Aspect;
import org.aspectj.lang.annotation.Before;
import org.aspectj.lang.annotation.Pointcut;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Component;
import org.springframework.web.context.request.RequestContextHolder;
import org.springframework.web.context.request.ServletRequestAttributes; import javax.servlet.http.HttpServletRequest; @Aspect
@Component
@Slf4j
public class RequestLogAspect {
@Autowired private EventPublisher eventPublisher;
private ThreadLocal<OperationLog> logThreadLocal = new ThreadLocal<>();
//拦截web下所有方法
@Pointcut("execution(* com.vian.admin.web..*.*(..))")
public void pointcut() {
log.info("拦截请求start");
} @Before("pointcut()")
public void doBefore(JoinPoint joinPoint) { ServletRequestAttributes attributes =
(ServletRequestAttributes) RequestContextHolder.getRequestAttributes();
HttpServletRequest request = attributes.getRequest();
String beanName = joinPoint.getSignature().getDeclaringTypeName();
String methodName = joinPoint.getSignature().getName();
String uri = request.getRequestURI();
String userId = SecurityUtils.getCurrentUserId();
//get方法不记录日志
if ("GET".equals(request.getMethod())) {
return;
}
//请求参数
Object[] paramsArray = joinPoint.getArgs();
log.info(
"请求日志拦截:userId={}, uri={}, method={}, request={}",
userId,
uri,
request.getMethod(),
paramsArray);
// 组装日志数据
OperationLog optLog = new OperationLog();
optLog.setUserId(userId);
optLog.setResource(uri);
optLog.setRequestMethod(request.getMethod());
optLog.setBeanName(beanName);
optLog.setMethodName(methodName);
optLog.setRequestParams(argsArrayToString(paramsArray));
logThreadLocal.set(optLog);
} @AfterReturning(returning = "result", pointcut = "pointcut()")
public void doAfterReturning(Object result) {
try {
// 处理完请求,从线程变量中获取日志数据,并记录到db
OperationLog optLog = logThreadLocal.get();
if (null != optLog) {
optLog.setResponseData(JSON.toJSONString(result));
eventPublisher.publish(new OperationLogEvent(this, optLog));
}
} catch (Exception e) {
log.error("***操作请求日志记录失败doAfterReturning()***", e);
} finally {
// 清除threadlocal
logThreadLocal.remove();
}
} /**
* 请求参数拼装
*
* @param paramsArray
* @return
*/
private String argsArrayToString(Object[] paramsArray) {
String params = "";
if (paramsArray != null && paramsArray.length > 0) {
for (int i = 0; i < paramsArray.length; i++) {
Object jsonObj = JSON.toJSON(paramsArray[i]);
params += jsonObj.toString() + " ";
}
}
return params.trim();
}
}

测试结果:

springboot springmvc拦截器 拦截POST、PUT、DELETE请求参数和响应数据,并记录操作日志的更多相关文章

  1. 防止SpringMVC拦截器拦截js等静态资源文件

    SpringMVC提供<mvc:resources>来设置静态资源,但是增加该设置如果采用通配符的方式增加拦截器的话仍然会被拦截器拦截,可采用如下方案进行解决: 方案一.拦截器中增加针对静 ...

  2. Springboot前后端分离中,后端拦截器拦截后,前端没有对应的返回码可以判断

    项目登录流程如下 用户进入前端登录界面,输入账号密码等,输入完成之后前端发送请求到后端(拦截器不会拦截登录请求),后端验证账号密码等成功之后生成Token并存储到数据库,数据库中包含该Token过期时 ...

  3. Springboot通过拦截器拦截请求信息收集到日志

    1.需求 最近在工作中遇到的一个需求,将请求中的客户端类型.操作系统类型.ip.port.请求方式.URI以及请求参数值收集到日志中,网上找资料说用拦截器拦截所有请求然后收集信息,于是就开始了操作: ...

  4. Struts2 拦截器—拦截action

    对于拦截器的基本使用这里我就懒得打字了,我这里就讲下如何用 Struts2 拦截器 拦截action.这是我个人的想法,如果有什么不对的,或者你们有什么更好的方法.请多多留言! 拦截器的默认拦截的方法 ...

  5. java端拦截器判断客户的的请求是否是ajax请求

    java端拦截器判断客户的的请求是否是ajax请求 发表于 2014-08-22 23:38:08 普通请求与ajax请求的报文头不一样,通过如下 String requestType = reque ...

  6. SpringMVC请求参数和响应结果全局加密和解密

    前提 前段时间在做一个对外的网关项目,涉及到加密和解密模块,这里详细分析解决方案和适用的场景.为了模拟真实的交互场景,先定制一下整个交互流程.第三方传输(包括请求和响应)数据报文包括三个部分: 1.t ...

  7. 使用SpringBoot AOP 记录操作日志、异常日志

    平时我们在做项目时经常需要对一些重要功能操作记录日志,方便以后跟踪是谁在操作此功能:我们在操作某些功能时也有可能会发生异常,但是每次发生异常要定位原因我们都要到服务器去查询日志才能找到,而且也不能对发 ...

  8. 扩展SpringMVC以支持绑定JSON格式的请求参数

    此方案是把请求参数(JSON字符串)绑定到java对象,,@RequestBody是绑定内容体到java对象的. 问题描述: <span style="font-size: x-sma ...

  9. 在JSP中常见问题,防止SpringMVC拦截器拦截js等静态资源文件的解决方案

    方案一.拦截器中增加针对静态资源不进行过滤(涉及spring-mvc.xml) <mvc:resources location="/" mapping="/**/* ...

随机推荐

  1. PIC单片机基础1

    1.PIC单片机总线结构——哈佛结构:即指令和数据空间是完全分开的,所以与常见的微控制器不同的一点是,程序和数据总线可以采用不同的宽度.以PIC16F684单片机为例,数据总线是8位的,但指令总线位数 ...

  2. Java三大特性

    Java 三大特性,算是Java独特的表现,提到Java 的三大特性, 我们都会想到封装, 继承和多态 这是我们Java 最重要的特性. 封装(Encapsulation) : 封装:是指隐藏对象的属 ...

  3. Django ORM 使用原生 SQL

    使用原生sql的 方法 : raw # row方法:(掺杂着原生sql和orm来执行的操作) res = CookBook.objects.raw('select id as nid from epo ...

  4. 浅谈background-size的几个属性值

    前言: css应用中,我们常会碰到background-size的用法,不妨下面总结一下,以便后续查看. 一.先弄个简单的box框. <!DOCTYPE html> <html la ...

  5. ios之库Protobuf的使用

    https://blog.csdn.net/dangbai01_/article/details/81099001 (1)Protobuf是什么? Protobuf 即 google protocol ...

  6. [百度百科]dir命令指定显示的排序方式

    https://jingyan.baidu.com/article/7c6fb428dcf39880642c9095.html 今天工作中遇到了这个需求 感觉很好用 dir /o:d >name ...

  7. ORACLE数据闪回

    ALTER TABLE SPM_CON_PAYMENT_RECEIPT ENABLE ROW MOVEMENT;   -- 表名 FLASHBACK TABLE SPM_CON_PAYMENT_REC ...

  8. 快速排序-python

  9. vue打包静态资源路径不正确的解决办法【转】

    vue项目完成打包上线的时候很多人都会碰到静态资源找不到的问题,常见的有两个 1.js,css路径不对 解决办法:打开config/index.js,将其中的assetsPublicPath值改为’. ...

  10. P3709 大爷的字符串题 (莫队)

    题目 P3709 大爷的字符串题 题意:求\([l,r]\)中众数的个数. 解析 维护两个数组: \(cnt[x]\),数\(x\)出现的次数. \(sum[x]\),出现次数为\(x\)的数的个数. ...