一、 一般微服务中日志记录
1 AOP切面记录
package com.xsy.aop;
import java.io.IOException;
import java.lang.reflect.Method;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import org.aspectj.lang.JoinPoint;
import org.aspectj.lang.ProceedingJoinPoint;
import org.aspectj.lang.annotation.AfterReturning;
import org.aspectj.lang.annotation.AfterThrowing;
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.aspectj.lang.reflect.MethodSignature;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.core.LocalVariableTableParameterNameDiscoverer;
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 com.xsy.entity.LoggerEntity;
/**
* 日志AOP
*
*
*/
@Aspect
@Component
public class WebLogAspect {
private final static Logger logger = LoggerFactory.getLogger(WebLogAspect.class);
public static final String X_USERID = "X-UserId";
public static final String X_REQUEST_ID = "X-Request-Id";
ThreadLocal<LoggerEntity> loggerEntityThreadLocal = new ThreadLocal<LoggerEntity>();
@Pointcut("execution(* com.xsy.controller..*.*(..)))")
public void webLog() {
}
/**
* 前置通知,方法调用前被调用
*
* @param joinPoint
*/
@Before(value = "webLog()")
public void doBefore(JoinPoint joinPoint) throws IOException {
// 接收到请求,记录请求内容
ServletRequestAttributes attributes = (ServletRequestAttributes) RequestContextHolder.getRequestAttributes();
HttpServletRequest request = attributes.getRequest();
// 创建日志实体
LoggerEntity loggerEntity = new LoggerEntity();
// 请求开始时间
loggerEntity.setStartTime(System.currentTimeMillis());
String userId = request.getHeader(X_USERID);
loggerEntity.setUserId(userId);
String uuid = request.getHeader(X_REQUEST_ID);
loggerEntity.setUuid(uuid);
// 请求路径
String url = request.getRequestURI();
// 获取请求参数信息
String paramData = JSON.toJSONString(request.getParameterMap(),
SerializerFeature.DisableCircularReferenceDetect, SerializerFeature.WriteMapNullValue);
loggerEntity.setParamData(paramData);
// 设置客户端ip
loggerEntity.setClientIp(getCliectIp(request));
// 设置请求方法 get post
loggerEntity.setRequestMethodType(request.getMethod());
// 设置请求类型(json|普通请求)
loggerEntity.setType(getRequestType(request));
// 设置请求地址
loggerEntity.setUri(url);
String sessionId = request.getRequestedSessionId();
//设置sessionId
loggerEntity.setSessionId(sessionId);
// 请求的类及名称
loggerEntity.setClassMethod(joinPoint.getSignature().getDeclaringTypeName() + "." + joinPoint.getSignature().getName());
// 设置请求方法
loggerEntity.setMethod(joinPoint.getSignature().getName());
loggerEntityThreadLocal.set(loggerEntity);
// 获取形参的名称
Method method = ((MethodSignature) (joinPoint.getSignature())).getMethod();
String[] parameterNames = new LocalVariableTableParameterNameDiscoverer().getParameterNames(method);
Object[] arguments = joinPoint.getArgs();
for (int i = 0; i < arguments.length; i++) {
try {
logger.info(JSON.toJSONString(parameterNames[i]) + ": " + JSON.toJSONString(arguments[i]));
} catch (Exception e) {
logger.info("未知传入参数");
}
}
}
/**
* 后置返回通知 这里需要注意的是: 如果参数中的第一个参数为JoinPoint,则第二个参数为返回值的信息
* 如果参数中的第一个参数不为JoinPoint,则第一个参数为returning中对应的参数 returning
* 限定了只有目标方法返回值与通知方法相应参数类型时才能执行后置返回通知,否则不执行,对于returning对应的通知方法参数为Object类型将匹配任何目标返回值
*
* @param joinPoint
* @param returnData
*/
@AfterReturning(value = "webLog()", returning = "returnData")
public void doAfterReturning(JoinPoint joinPoint, Object returnData) {
ServletRequestAttributes attributes = (ServletRequestAttributes) RequestContextHolder.getRequestAttributes();
HttpServletResponse response = attributes.getResponse();
// 获取请求错误码
int status = response.getStatus();
// 获取本次请求日志实体
LoggerEntity loggerEntity = loggerEntityThreadLocal.get();
// 请求结束时间
loggerEntity.setEndTime(System.currentTimeMillis());
// 设置请求时间差
loggerEntity.setCostTime(Integer.valueOf((loggerEntity.getEndTime() - loggerEntity.getStartTime()) + ""));
// 设置返回错误码
loggerEntity.setHttpStatusCode(status + "");
// 设置返回值
loggerEntity.setReturnData(JSON.toJSONString(returnData, SerializerFeature.DisableCircul