【SpringBoot】配置日志

示例

【SpringBoot】配置日志_第1张图片
image

日志格式

{
    "getParameter": {
        "accessToken": "eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzUxMiJ9.eyJwaG90b1VybCI6IiIsInBob25lTnVtYmVyIjoiMTg1NzE2MDEwNTAiLCJuYW1lIjoi6YOt5Y2X5p6XIiwiZXhwIjoxNTc3ODU3NTcxLCJ1c2VySWQiOiIxIiwic3VwcG9ydCI6dHJ1ZSwiZW1haWwiOiI2NTM0NjgzODBAcXEuY29tIn0.nYyRAU0muuk-tP7RfoXBWAznCoGOESAeJhvWk7KjGv6queUD2d1BI4K_UO35x_Erj-kDZpH5doLpAEzIfNUj5g"
    },
    "postParameter": [],
    "requestMethod": "GET",
    "requestURL": "http://localhost:8080/auth/user",
    "returnValue": {
        "code": 200,
        "data": {
            "email": "[email protected]",
            "id": "1",
            "name": "郭南林",
            "phoneNumber": "18500000000",
            "photoUrl": "",
            "support": true
        },
        "message": "操作成功"
    },
    "timeConsuming": 3,
    "userId": "1"
}

目录结构

【SpringBoot】配置日志_第2张图片

yml配置

logging:
  config: classpath:logback-boot.xml

logback-boot.xml



    
    
    
    
        
            %d %p (%file:%line\)- %m%n
            
            UTF-8
        
    
    
    
    
    
    
        log/server.log
        
        
        
            
            
            
            log/server.%d.%i.log
            
            30
            
                
                10MB
            
        
        
            
            %d{yyyy-MM-dd HH:mm:ss.SSS} [%thread] %-5level %logger{50} - %msg%n
            
            UTF-8
        
    
    
    
    
    
        
        
        
        
    
    
    
    

如果控制台不想输出日志可以将注释掉。

LogEntry日志条目实体类

public class LogEntry {

    private String userId;
    private String requestURL;
    private String requestMethod;
    private Object getParameter;
    private Object postParameter;
    private long timeConsuming;
    private Object returnValue;

    public String getUserId() {
        return userId;
    }

    public void setUserId(String userId) {
        this.userId = userId;
    }

    public String getRequestURL() {
        return requestURL;
    }

    public void setRequestURL(String requestURL) {
        this.requestURL = requestURL;
    }

    public String getRequestMethod() {
        return requestMethod;
    }

    public void setRequestMethod(String requestMethod) {
        this.requestMethod = requestMethod;
    }

    public Object getGetParameter() {
        return getParameter;
    }

    public void setGetParameter(Object getParameter) {
        this.getParameter = getParameter;
    }

    public Object getPostParameter() {
        return postParameter;
    }

    public void setPostParameter(Object postParameter) {
        this.postParameter = postParameter;
    }

    public long getTimeConsuming() {
        return timeConsuming;
    }

    public void setTimeConsuming(long timeConsuming) {
        this.timeConsuming = timeConsuming;
    }

    public Object getReturnValue() {
        return returnValue;
    }

    public void setReturnValue(Object returnValue) {
        this.returnValue = returnValue;
    }

    public LogEntry() {
        super();
        // TODO Auto-generated constructor stub
    }

    public LogEntry(String userId, String requestURL, String requestMethod, Object getParameter, Object postParameter,
            long timeConsuming, Object returnValue) {
        super();
        this.userId = userId;
        this.requestURL = requestURL;
        this.requestMethod = requestMethod;
        this.getParameter = getParameter;
        this.postParameter = postParameter;
        this.timeConsuming = timeConsuming;
        this.returnValue = returnValue;
    }

}

Controller通用日志切面类

此切面类只适用于返回数据为纯JSON格式的,返回界面view会报错。

import java.util.Arrays;
import java.util.Enumeration;
import java.util.HashMap;
import java.util.List;
import java.util.Map;

import javax.servlet.http.HttpServletRequest;

import org.aspectj.lang.JoinPoint;
import org.aspectj.lang.ProceedingJoinPoint;
import org.aspectj.lang.annotation.AfterReturning;
import org.aspectj.lang.annotation.Around;
import org.aspectj.lang.annotation.Aspect;
import org.aspectj.lang.annotation.Before;
import org.aspectj.lang.annotation.Pointcut;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.stereotype.Component;
import org.springframework.web.context.request.RequestContextHolder;
import org.springframework.web.context.request.ServletRequestAttributes;

import com.alibaba.fastjson.JSON;
import com.alibaba.fastjson.serializer.SerializerFeature;

import gnl.tool.account.dto.UserThreadLocal;
import gnl.tool.common.dto.AccountDto;
import gnl.tool.common.log.LogEntry;

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

    /**
     * ~ *:代表任意修饰符及任意返回值 
     * ~ *:任意类 
     * ~ *:任意方法 
     * ~ (..):任意参数
     */
    @Pointcut("execution(* gnl.tool.account.controller.*.*(..))")
    public void webLog() { }

    @Before("webLog()")
    public void doBefore(JoinPoint joinPoint) { }

    // returning的值和doAfterReturning的参数名一致
    @AfterReturning(returning = "ret", pointcut = "webLog()") 
    public void doAfterReturning(Object ret) throws Throwable { }

    @Around("webLog()")
    public Object doAround(ProceedingJoinPoint pjp) throws Throwable {
        // 请求开始时间
        long startTime = System.currentTimeMillis();

        // 接收到请求,记录请求内容
        ServletRequestAttributes attributes = (ServletRequestAttributes) RequestContextHolder.getRequestAttributes();
        HttpServletRequest request = attributes.getRequest();

        // get请求参数
        Enumeration parameterNames = request.getParameterNames();
        Map map = new HashMap<>();
        while (parameterNames.hasMoreElements()) {
            String key = parameterNames.nextElement();
            String value = request.getParameter(key);
            map.put(key, value);
        }

        // post请求參數
        List postList = Arrays.asList(pjp.getArgs());

        // ob为方法的返回值
        Object ob = pjp.proceed();

        // 请求人信息
        AccountDto accountDto = UserThreadLocal.get();
        String userId = null;
        if(accountDto != null) {
            userId = accountDto.getId();
        }

        // 记录请求日志
        LogEntry logEntry = new LogEntry(userId, request.getRequestURL().toString(), request.getMethod(), map,
                postList, System.currentTimeMillis() - startTime, ob);
        
        log.info("网络请求:{}", JSON.toJSONString(logEntry,SerializerFeature.DisableCircularReferenceDetect));
        
        return ob;
    }

}
 

                            
                        
                    
                    
                    

你可能感兴趣的:(【SpringBoot】配置日志)