springboot 切面日志记录

复制代码
package com.web.aspect;


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.slf4j.MDC;
import org.springframework.context.annotation.Configuration;
import org.springframework.web.context.request.RequestContextHolder;
import org.springframework.web.context.request.ServletRequestAttributes;

import javax.servlet.http.HttpServletRequest;
import java.util.*;


/**
 */
@Slf4j
@Aspect
@Configuration
public class LogAspect {

    @Pointcut("execution(* com.web.controller..*.*(..))")
    private void controllerAspect(){
    }

    @Before(value = "controllerAspect()")
    public void invokeBefore(JoinPoint point) {
        String realClassName = getRealClassName(point);
        String traceId = UUID.randomUUID().toString().replace("-", "");
        MDC.put("traceId", traceId);
        if (canPrintLog(point)) {
            log.info("invoke class: {}, execute method: {}, requestParams: {},header: {}", realClassName, getMethodName(point), getRequestParams(point),getRequestHeaderInfo());
        }
    }

    @AfterReturning(pointcut = "controllerAspect()",returning="returnValue")
    public void invokeAfter(JoinPoint point, Object returnValue) {
        String realClassName = getRealClassName(point);
        if (canPrintLog(point)) {
            log.info("invoke class: {}, execute method: {}", realClassName, getMethodName(point));
        }
        MDC.clear();
    }


    private String getRealClassName(JoinPoint point) {
        return point.getTarget().getClass().getName();
    }

    private String getMethodName(JoinPoint point) {
        return point.getSignature().getName();
    }


    private List<Object> getRequestParams(JoinPoint point) {
        List<Object> params = new ArrayList<>();
        Object[] args = point.getArgs();
        for (Object arg: args) {
            if (arg instanceof PropertyUser) {
                PropertyUser obj = new PropertyUser();
                PropertyUser user = (PropertyUser)arg;
                obj.setUserId(user.getUserId());
                obj.setUserName(user.getUserName());
                params.add(obj);
            } else {
                params.add(arg);
            }
        }
        return params;
    }

    private boolean canPrintLog(JoinPoint point) {
        List<String> canNotPrintLog = new ArrayList<>();
        return !canNotPrintLog.contains(point.getSignature().getName());
    }

    private Map<String,String> getRequestHeaderInfo(){
        ServletRequestAttributes sra =  (ServletRequestAttributes)RequestContextHolder.getRequestAttributes();
        HttpServletRequest request = sra.getRequest();
        Enumeration<String> enumeration = request.getHeaderNames();
        Map<String,String> headerMap = Maps.newHashMap();
        while (enumeration.hasMoreElements()) {
            String name = enumeration.nextElement();
            if(!"cookie".equals(name)){
                headerMap.put(name,request.getHeader(name));
            }
        }
        return headerMap;
    }
}
复制代码

 

posted @   甜菜波波  阅读(321)  评论(0编辑  收藏  举报
编辑推荐:
· 基于Microsoft.Extensions.AI核心库实现RAG应用
· Linux系列:如何用heaptrack跟踪.NET程序的非托管内存泄露
· 开发者必知的日志记录最佳实践
· SQL Server 2025 AI相关能力初探
· Linux系列:如何用 C#调用 C方法造成内存泄露
阅读排行:
· 无需6万激活码!GitHub神秘组织3小时极速复刻Manus,手把手教你使用OpenManus搭建本
· Manus爆火,是硬核还是营销?
· 终于写完轮子一部分:tcp代理 了,记录一下
· 别再用vector<bool>了!Google高级工程师:这可能是STL最大的设计失误
· 单元测试从入门到精通
点击右上角即可分享
微信分享提示