springboot AOP 攔截獲取記錄日志信息


1.添加依賴

通過spring boot創建好工程后,添加如下依賴,不然工程中無法使用切面的注解,就無法對制定的方法進行攔截

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

 

2. 自定義注解類 LogRequest

 

/**
 * @ClassNameLogRequest.java
 * @author shengwu
 * @date 2019-10-19
 * @Target 此注解的作用目標,括號里METHOD的意思說明此注解只能加在方法上面
 * @Retention 注解的保留位置,括號里RUNTIME的意思說明注解可以存在於運行時,可以用於反射
 * @Documented 說明該注解將包含在javadoc中
 */
@Target(ElementType.METHOD)
@Retention(RetentionPolicy.RUNTIME)
@Documented
public @interface LogRequest {
    /**
     * 是否記錄日志表中
     * @return
     */
    String logFlag() default "N";

    /**
     * 接口名稱
     * @return
     */
    String interfaceName() default "";
}

 

3. 切面類

 

import org.aspectj.lang.JoinPoint;
import org.aspectj.lang.ProceedingJoinPoint;
import org.aspectj.lang.annotation.Around;
import org.aspectj.lang.annotation.Aspect;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
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;

/**
 * 此類為一個切面類,主要作用就是對接口的請求進行攔截
 * 攔截的方式,只需要在指定接口方法上面加上@LogRequest注解即可
 *
 * @author shengwu
 * @version 1.0
 * @since 2019/09/28
 */
@Aspect
@Component
public class RequestAspect {
    private static final Logger logger = LoggerFactory.getLogger(RequestAspect.class);
    @Autowired
    private IInterfaceLogService iInterfaceLogService;
    /**
     * 表示在執行被@LogRequest注解修飾的方法之前 會執行doBefore()方法
     *
     * @param joinPoint 連接點,就是被攔截點
     */
    @Around(value = "@annotation(LogRequest)")
    public Object doAround(ProceedingJoinPoint joinPoint, LogRequest LogRequest) throws Throwable {
        Long start = System.currentTimeMillis();
        try {
            Object result = joinPoint.proceed();
            this.methodAround(joinPoint,result,start,LogRequest.logFlag(),LogRequest.interfaceName(),true);
            return result;
        } catch (Throwable throwable) {
            throwable.printStackTrace();
            this.methodAround(joinPoint,throwable.getMessage(),start,LogRequest.logFlag(),LogRequest.interfaceName(),false);
            throw throwable;
        }
    }

}

4. 日志方法

 /**
     *
     * @param joinPoint
     * @param object 返回對象值
     * @param startTime 方法開始時間
     * @param logFlag 是否插入日志
     * @param requestStatus 本次請求狀態
     *
     */
    public void methodAround(JoinPoint joinPoint,Object object,Long startTime,String logFlag,String interfaceName,Boolean requestStatus) {
        //獲取到請求的屬性
        ServletRequestAttributes attributes = (ServletRequestAttributes)RequestContextHolder.getRequestAttributes();
        //獲取到請求對象
        HttpServletRequest request = attributes.getRequest();
        //URL:根據請求對象拿到訪問的地址
        logger.info("url={}" , request.getRequestURL());
        logger.info("接口名稱={}" , interfaceName);
        logger.info("代理對象自己:{}" + joinPoint.getThis());
        //獲取傳入目標方法的參數
        Object[] args = joinPoint.getArgs();
        Long time = (System.currentTimeMillis()-startTime);
        logger.info("執行時間長{}",time);
        Long endTime = System.currentTimeMillis();
        Date date = new Date(startTime);
        InterfaceLogDTO interfaceLogDTO = new InterfaceLogDTO();
        String uuid = UUID.randomUUID().toString();
        interfaceLogDTO.setInvokeKey(uuid);
        //微服務應用名
        interfaceLogDTO.setServerCode(serverCode);
        interfaceLogDTO.setRequestTime(date);
        interfaceLogDTO.setInterfaceResponseTime(endTime-startTime);
        interfaceLogDTO.setServerName(interfaceName);
        interfaceLogDTO.setApplicationCode(applicationInitListener.getServerIpPort());
        interfaceLogDTO.setUserAgent(request.getHeader("user-agent"));
        CustomUserDetails customClient = DetailsHelper.getUserDetails();
        if (customClient==null||customClient.getOrganizationId()==null) {
            logger.error("接口"+interfaceName+"租戶獲取空");
            return;
        }
        interfaceLogDTO.setTenantId(customClient.getOrganizationId());
        interfaceLogDTO.setClientId(customClient.getClientId()==null?null:String.valueOf(customClient.getClientId()));
        interfaceLogDTO.setInterfaceUrl(request.getRequestURL().toString());
        interfaceLogDTO.setRequestMethod(request.getMethod());
        interfaceLogDTO.setIp(request.getRemoteAddr());
        interfaceLogDTO.setInterfaceRequestTime(date);
        //明細
        InterfaceLogDtlDTO interfaceLogDtlDTO = new InterfaceLogDtlDTO();
        interfaceLogDTO.setInterfaceLogDtlDTO(interfaceLogDtlDTO);
        interfaceLogDtlDTO.setInvokeKey(uuid);
        StringBuilder stringBuilder = new StringBuilder();
        for (int i = 0; i < args.length; i++) {
            try {
                stringBuilder.append(objectMapper.writeValueAsString(args[i]));
            } catch (JsonProcessingException e) {
                e.printStackTrace();
            }
        }
        interfaceLogDtlDTO.setInterfaceReqBodyParam(stringBuilder.toString());
        String interfaceRespContent =null;
        try {
            if (result!=null) {
                //返回內容
                interfaceRespContent = objectMapper.writeValueAsString(result);
            }

        } catch (JsonProcessingException e) {
            e.printStackTrace();
        }
        if (requestStatus){
            interfaceLogDtlDTO.setInterfaceRespContent(interfaceRespContent);
            interfaceLogDTO.setResponseStatus(SUCCESS);
            interfaceLogDTO.setInterfaceResponseStatus(SUCCESS);
        }
        if (!requestStatus){
            interfaceLogDtlDTO.setStacktrace(interfaceRespContent);
            interfaceLogDTO.setResponseStatus(FAIL);
            interfaceLogDTO.setInterfaceResponseStatus(FAIL);
        }
        if(!FLAG_Y.equals(logFlag)){
            logger.info("出站信息{}",interfaceLogDTO.toString());
            return;
        }
    }

 


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM