Spring Cloud Sleuth是一個在應用中實現日志跟蹤的強有力的工具。使用Sleuth庫可以應用於計划任務 、多線程服務或復雜的Web請求,尤其是在一個由多個服務組成的系統中。當我們在這些應用中來診斷問題時,即使有日志記錄也很難判斷出一個請求需要將哪些操作關聯在一起。
如果想要診斷復雜操作,通常的解決方案是在請求中傳遞唯一的ID到每個方法來識別日志。而Sleuth可以與日志框架Logback、SLF4J輕松地集成,通過添加獨特的標識符來使用日志跟蹤和診斷問題。
<dependency> <groupId>org.springframework.cloud</groupId> <artifactId>spring-cloud-starter-sleuth</artifactId> <version>2.1.1.RELEASE</version> </dependency>
SLF4J 配置 https://www.cnblogs.com/baobaoxiaokeai/p/11017329.html
在使用slf4j打印日志時會打印traceId,通過這ID可以把整個請求鏈給找出來.
如下是打印出來的實例
2019-06-19 17:16:21.453 [00c62017e97b7823,00c62017e97b7823] [http-nio-8777-exec-1]
需要把traceId給前端,使用aop,在每個返回結果中增加traceId字段
import brave.Tracer; import com.alibaba.fastjson.JSON; import com.alibaba.fastjson.JSONObject; import lombok.extern.slf4j.Slf4j; import org.aspectj.lang.ProceedingJoinPoint; import org.aspectj.lang.annotation.Around; import org.aspectj.lang.annotation.Aspect; import org.aspectj.lang.annotation.Pointcut; import org.springframework.beans.factory.annotation.Autowired; import org.springframework.context.annotation.Configuration; import org.springframework.web.context.request.RequestAttributes; import org.springframework.web.context.request.RequestContextHolder; import org.springframework.web.context.request.ServletRequestAttributes; import com.google.gson.Gson; import org.slf4j.Logger; import org.slf4j.LoggerFactory;;import javax.servlet.http.HttpServletRequest; @Aspect //定義一個切面 @Configuration @Slf4j public class TraceAspect { // 定義切點Pointcut @Pointcut("execution(* com.gf.controller..*.*(..))") public void excudeService() { } @Autowired Tracer tracer; @Around("excudeService()") public Object doAround(ProceedingJoinPoint pjp) throws Throwable { RequestAttributes ra = RequestContextHolder.getRequestAttributes(); ServletRequestAttributes sra = (ServletRequestAttributes) ra; HttpServletRequest request = sra.getRequest(); String url = request.getRequestURL().toString(); String method = request.getMethod(); String uri = request.getRequestURI(); String queryString = request.getQueryString(); log.info("請求開始, 各個參數, url: {}, method: {}, uri: {}, params: {}", url, method, uri, queryString); // result的值就是被攔截方法的返回值 Object result = pjp.proceed(); JSONObject dd = JSONObject.parseObject(JSON.toJSONString(result)); dd.put("traceId",tracer.currentSpan().context().traceIdString()); log.info("請求結束,controller的返回值是 {} - {}", tracer.currentSpan().toString(), dd.toJSONString()); return dd; } }
轉載自:https://blog.csdn.net/peterwanghao/article/details/79967634