1. <strong id="7actg"></strong>
    2. <table id="7actg"></table>

    3. <address id="7actg"></address>
      <address id="7actg"></address>
      1. <object id="7actg"><tt id="7actg"></tt></object>

        Spring Boot 使用 AOP 記錄日志

        共 7499字,需瀏覽 15分鐘

         ·

        2021-03-04 09:13


        在項目開發(fā)中經常,日志系統(tǒng)是必不可少的,特別是管理系統(tǒng),對于重要的操作都會有操作日志,然而這個操作不需要我們在相應的方法中一個一個的去實現(xiàn),這肯定是不合適的,這樣的操作無疑是加大了開發(fā)量,而且不易維護,所以實際項目中總是利用AOP(Aspect Oriented Programming)即面向切面編程來記錄系統(tǒng)中的操作日志。

        下面就來介紹如何在 Spring Boot 中 使用 AOP 記錄日志:

        加入依賴

        首先加入 AOP 依賴:

        <dependency>
         <groupId>org.springframework.boot</groupId>
         <artifactId>spring-boot-starter-aop</artifactId>
        </dependency>

        創(chuàng)建日志注解類

        創(chuàng)建一個日志注解類,這樣就可以在需要記錄日志的方法上加上注解就可以記錄日志了,注解內容如下:

        @Target({ElementType.PARAMETER, ElementType.METHOD})
        @Retention(RetentionPolicy.RUNTIME)
        @Documented
        public @interface AopLogger {

            String describe() default "";
        }

        配置 AOP 切面

        定義一個 AopLoggerAspect 切面類,用 @Aspect 聲明該類為切面類。

        @Aspect
        @Component
        public class AopLoggerAspect {
            private final Logger logger = LoggerFactory.getLogger(this.getClass());

            @Pointcut("@annotation(com.wupx.aop.logger.annotation.AopLogger)")
            public void aopLoggerAspect() {
            }

            /**
             * 環(huán)繞觸發(fā)
             *
             * @param point
             * @return
             */
            @Around("aopLoggerAspect()")
            public Object doAround(ProceedingJoinPoint point) {
                RequestAttributes requestAttributes = RequestContextHolder.getRequestAttributes();
                ServletRequestAttributes servletRequestAttributes = (ServletRequestAttributes) requestAttributes;
                HttpServletRequest request = servletRequestAttributes.getRequest();
                Object result = null;
                long startTime = System.currentTimeMillis();
                try {
                    result = point.proceed();
                } catch (Throwable throwable) {
                    throwable.printStackTrace();
                    logger.error(throwable.getMessage());
                }
                String describe = getAopLoggerDescribe(point);
                if (StringUtils.isBlank(describe)) {
                    describe = "-";
                }
                // 打印請求相關參數
                logger.info("========================================== Start ==========================================");
                logger.info("Describe       : {}", describe);
                // 打印請求 url
                logger.info("URL            : {}", request.getRequestURL());
                logger.info("URI            : {}", request.getRequestURI());
                // 打印 Http method
                logger.info("HTTP Method    : {}", request.getMethod());
                // 打印調用 controller 的全路徑以及執(zhí)行方法
                logger.info("Class Method   : {}.{}", point.getSignature().getDeclaringTypeName(), point.getSignature().getName());
                // 打印請求的 IP
                logger.info("IP             : {}", request.getRemoteAddr());
                // 打印請求入參
                logger.info("Request Args   : {}", point.getArgs());
                // 打印請求出參
                logger.info("Response Args  : {}", result);
                logger.info("Time Consuming : {} ms", System.currentTimeMillis() - startTime);
                logger.info("=========================================== End ===========================================");
                return result;
            }

            /**
             * 獲取注解中對方法的描述信息
             *
             * @param joinPoint 切點
             * @return describe
             */
            public static String getAopLoggerDescribe(JoinPoint joinPoint) {
                MethodSignature signature = (MethodSignature) joinPoint.getSignature();
                Method method = signature.getMethod();
                AopLogger controllerLog = method.getAnnotation(AopLogger.class);
                return controllerLog.describe();
            }
        }

        其中 「@Pointcut」 是定義一個切點,后面跟隨一個表達式,表達式可以定義為某個 package 下的方法,也可以是自定義注解等。

        「@Around」 為在切入點前后織入代碼,并且可以自由的控制何時執(zhí)行切點。

        測試

        接下來編寫 Controller 層來進行測試:

        @RestController
        @RequestMapping("/user")
        public class UserController {

            private final UserService userService;

            public UserController(UserService userService) {
                this.userService = userService;
            }

            @PostMapping
            @AopLogger(describe = "添加用戶")
            public String addUser(@RequestBody User user) {
                UserEntity userEntity = new UserEntity();
                BeanUtils.copyProperties(user, userEntity);
                return userService.addUser(userEntity);
            }
        }

        只需要在接口上填寫 @AopLogger 就可以記錄操作日志。

        啟動服務,通過 PostMan 請求 http://localhost:8080/user 接口,輸出的日志如下所示:

        可以看到把入參、出參以及接口信息都記錄了下來,是不是很簡單呢,只需要簡單幾步就可以實現(xiàn) AOP 日志,大家可以自己實踐下。

        本文的完整代碼在 https://github.com/wupeixuan/SpringBoot-Learnaop-logger 目錄下。

        瀏覽 74
        點贊
        評論
        收藏
        分享

        手機掃一掃分享

        分享
        舉報
        評論
        圖片
        表情
        推薦
        點贊
        評論
        收藏
        分享

        手機掃一掃分享

        分享
        舉報
        1. <strong id="7actg"></strong>
        2. <table id="7actg"></table>

        3. <address id="7actg"></address>
          <address id="7actg"></address>
          1. <object id="7actg"><tt id="7actg"></tt></object>
            美女很黄很黄免费的 | 久久99偷拍视频 | 久久精品视频播放 | 天天爽夜夜爽夜夜爽精品视频 | m.m视频在线观看 | 欧美激情国产在线 | 狠狠操在线视频 | 青娱乐无码 | 一级毛片AAAAAA免费看小说 | 自拍偷拍视频二区 |