当前位置:   article > 正文

SpringBoot 切片做请求接口日志_spring 代码如何在日志切面层面获取 post json 请求参数 而不影响业务使用

spring 代码如何在日志切面层面获取 post json 请求参数 而不影响业务使用

如何在 Spring Boot 2.0 中使用 AOP 切面统一处理请求日志,打印进出参相关参数。

一:先看看日志输出效果

可以看到,每个对于每个请求,开始与结束一目了然,并且打印了以下参数:

  • URL: 请求接口地址;
  • HTTP Method: 请求的方法,是 POSTGET, 还是 DELETE 等;
  • Class Method: 对应 Controller 的全路径以及调用的哪个方法;
  • IP: 请求 IP 地址;
  • Request Args: 请求入参,以 JSON 格式输出;
  • Response Args: 响应出参,以 JSON 格式输出;
  • Time-Consuming: 请求耗时;

二:添加 Maven 依赖

  1. <!-- aop 依赖 -->
  2. <dependency>
  3. <groupId>org.springframework.boot</groupId>
  4. <artifactId>spring-boot-starter-aop</artifactId>
  5. </dependency>
  6. <!-- https://mvnrepository.com/artifact/com.alibaba/fastjson -->
  7. <dependency>
  8. <groupId>com.alibaba</groupId>
  9. <artifactId>fastjson</artifactId>
  10. <version>1.2.47</version>
  11. </dependency>

三:配置 AOP 切面

在配置 AOP 切面之前,我们需要了解下 aspectj 相关注解的作用:

  • @Aspect:声明该类为一个注解类;
  • @Pointcut:定义一个切点,后面跟随一个表达式,表达式可以定义为某个 package 下的方法,也可以是自定义注解等;
  • 切点定义好后,就是围绕这个切点做文章了:
    • @Before: 在切点之前,织入相关代码;
    • @After: 在切点之后,织入相关代码;
    • @AfterReturning: 在切点返回内容后,织入相关代码,一般用于对返回值做些加工处理的场景;
    • @AfterThrowing: 用来处理当织入的代码抛出异常后的逻辑处理;
    • @Around: 在切入点前后织入代码,并且可以自由的控制何时执行切点;
  1. package com.zhx.guides.collect.web.aspect;
  2. import com.alibaba.fastjson.JSONObject;
  3. import org.aspectj.lang.JoinPoint;
  4. import org.aspectj.lang.ProceedingJoinPoint;
  5. import org.aspectj.lang.annotation.*;
  6. import org.slf4j.Logger;
  7. import org.slf4j.LoggerFactory;
  8. import org.springframework.stereotype.Component;
  9. import org.springframework.web.context.request.RequestContextHolder;
  10. import org.springframework.web.context.request.ServletRequestAttributes;
  11. import javax.servlet.http.HttpServletRequest;
  12. /**
  13. * @Class WebLogAspect
  14. * @Author 作者姓名:悟能的师兄
  15. * @Version 1.0
  16. * @Date 创建时间:2020-03-03 10:05
  17. * @Copyright Copyright by
  18. * @Direction 类说明
  19. */
  20. @Aspect
  21. @Component
  22. public class WebLogAspect {
  23. private final static Logger logger = LoggerFactory.getLogger(WebLogAspect.class);
  24. /** 以 controller 包下定义的所有请求为切入点 */
  25. @Pointcut("execution(public * com.zhx.guides.collect.interfaces.controller..*.*(..))")
  26. public void webLog() {}
  27. /**
  28. * 在切点之前织入
  29. * @param joinPoint
  30. * @throws Throwable
  31. */
  32. @Before("webLog()")
  33. public void doBefore(JoinPoint joinPoint) throws Throwable {
  34. // 开始打印请求日志
  35. ServletRequestAttributes attributes = (ServletRequestAttributes) RequestContextHolder.getRequestAttributes();
  36. HttpServletRequest request = attributes.getRequest();
  37. // 打印请求相关参数
  38. logger.info("======================= Start ======================");
  39. // 打印请求 url
  40. logger.info("URL : {}", request.getRequestURL().toString());
  41. // 打印 Http method
  42. logger.info("HTTP Method : {}", request.getMethod());
  43. // 打印调用 controller 的全路径以及执行方法
  44. logger.info("Class Method : {}.{}", joinPoint.getSignature().getDeclaringTypeName(), joinPoint.getSignature().getName());
  45. // 打印请求的 IP
  46. logger.info("IP : {}", request.getRemoteAddr());
  47. // 打印请求入参
  48. try {
  49. Object requestParam = joinPoint.getArgs();
  50. logger.info("参数 : {}", JSONObject.toJSONString(requestParam) );
  51. }catch (Exception e){
  52. logger.info("参数打印失败,异常: {}", e.getMessage() );
  53. }
  54. }
  55. /**
  56. * 在切点之后织入
  57. * @throws Throwable
  58. */
  59. @After("webLog()")
  60. public void doAfter() throws Throwable {
  61. logger.info("======================= End ======================");
  62. }
  63. /**
  64. * 环绕
  65. * @param proceedingJoinPoint
  66. * @return
  67. * @throws Throwable
  68. */
  69. @Around("webLog()")
  70. public Object doAround(ProceedingJoinPoint proceedingJoinPoint) throws Throwable {
  71. long startTime = System.currentTimeMillis();
  72. Object result = proceedingJoinPoint.proceed();
  73. // 打印出参
  74. logger.info("返回值 : {}", JSONObject.toJSONString(result));
  75. // 执行耗时
  76. logger.info("耗时 : {} ms", System.currentTimeMillis() - startTime);
  77. return result;
  78. }
  79. }

我们通过 @Aspect 声明了 WebLogAspect.java 为切面类,之后,通过 @Pointcut 定义了打印请求日志的切点,切点为 com.zhx.guides.collect.interfaces.controller 包下所有的请求接口。

切点定义好后,我们通过 @Before 在切点之前打印请求的相关参数,通过 @Around 打印了请求接口的耗时时间,最后通过 @After 做了请求的收尾工作。

到这里,切面相关的代码就完成了!

声明:本文内容由网友自发贡献,不代表【wpsshop博客】立场,版权归原作者所有,本站不承担相应法律责任。如您发现有侵权的内容,请联系我们。转载请注明出处:https://www.wpsshop.cn/w/你好赵伟/article/detail/940178
推荐阅读
相关标签
  

闽ICP备14008679号