当前位置:网站首页>从 1.5 开始搭建一个微服务框架——调用链追踪 traceId
从 1.5 开始搭建一个微服务框架——调用链追踪 traceId
2022-07-06 00:33:00 【InfoQ】
前言
1
核心功能
- 多个微服务模块拆分,抽取出一个 demo 微服务模块供扩展,已完成
- 提取核心框架模块,已完成
- 注册中心 Eureka,已完成
- 远程调用 OpenFeign,已完成
- 日志 logback,包含 traceId 跟踪,已完成
- Swagger API 文档,已完成
- 配置文件共享,已完成
- 日志检索,ELK Stack,已完成
- 自定义 Starter,待定
- 整合缓存 Redis,Redis 哨兵高可用,已完成
- 整合数据库 MySQL,MySQL 高可用,已完成
- 整合 MyBatis-Plus,已完成
- 链路追踪组件,待定
- 监控,待定
- 工具类,待开发
- 网关,技术选型待定
- 审计日志进入 ES,待定
- 分布式文件系统,待定
- 定时任务,待定
- 等等
一、痛点
痛点一:进程内的多条日志无法追踪

痛点二:跨服务的日志如何进行关联

痛点三:跨线程的日志如何关联

痛点四:第三方调用我们的服务,如何追踪?
二、方案
1.1 解决方案
1.2 MDC 方案
三、原理和实战
2.1 追踪一个请求的多条日志

<pattern>%d{yyyy-MM-dd HH:mm:ss.SSS} [%thread] %X{traceId} %-5level %logger - %msg%n</pattern>
header
traceId

示例代码
/**
* @author www.passjava.cn,公众号:悟空聊架构
* @date 2022-07-05
*/
@Service
public class LogInterceptor extends HandlerInterceptorAdapter {
private static final String TRACE_ID = "traceId";
@Override
public boolean preHandle(HttpServletRequest request, HttpServletResponse response, Object handler) throws Exception {
String traceId = request.getHeader(TRACE_ID);
if (StringUtils.isEmpty(traceId)) {
MDC.put("traceId", UUID.randomUUID().toString());
} else {
MDC.put(TRACE_ID, traceId);
}
return true;
}
@Override
public void postHandle(HttpServletRequest request, HttpServletResponse response, Object handler, ModelAndView modelAndView) throws Exception {
//防止内存泄露
MDC.remove("traceId");
}
}
/**
* @author www.passjava.cn,公众号:悟空聊架构
* @date 2022-07-05
*/
@Configuration
public class InterceptorConfig implements WebMvcConfigurer {
@Resource
private LogInterceptor logInterceptor;
@Override
public void addInterceptors(InterceptorRegistry registry) {
registry.addInterceptor(logInterceptor).addPathPatterns("/**");
}
}
2.2 跨服务跟踪多条日志

/**
* @author www.passjava.cn,公众号:悟空聊架构
* @date 2022-07-05
*/
@Configuration
public class FeignInterceptor implements RequestInterceptor {
private static final String TRACE_ID = "traceId";
@Override
public void apply(RequestTemplate requestTemplate) {
requestTemplate.header(TRACE_ID, (String) MDC.get(TRACE_ID));
}
}

四、总结
边栏推荐
- FFMPEG关键结构体——AVFormatContext
- Uniapp development, packaged as H5 and deployed to the server
- Global and Chinese market of valve institutions 2022-2028: Research Report on technology, participants, trends, market size and share
- STM32 key chattering elimination - entry state machine thinking
- 【DesignMode】组合模式(composite mode)
- MDK debug时设置数据实时更新
- 《编程之美》读书笔记
- How to use the flutter framework to develop and run small programs
- FFT learning notes (I think it is detailed)
- XML Configuration File
猜你喜欢
Atcoder beginer contest 258 [competition record]
Gd32f4xx UIP protocol stack migration record
Search (DFS and BFS)
N1 # if you work on a metauniverse product [metauniverse · interdisciplinary] Season 2 S2
时间戳的拓展及应用实例
如何制作自己的機器人
Classic CTF topic about FTP protocol
Leetcode 450 deleting nodes in a binary search tree
How to make your own robot
Idea remotely submits spark tasks to the yarn cluster
随机推荐
Knowledge about the memory size occupied by the structure
Common API classes and exception systems
【DesignMode】装饰者模式(Decorator pattern)
MySql——CRUD
Pointer - character pointer
Uniapp development, packaged as H5 and deployed to the server
Global and Chinese markets of universal milling machines 2022-2028: Research Report on technology, participants, trends, market size and share
About the slmgr command
Go learning --- structure to map[string]interface{}
Ffmpeg learning - core module
如何解决ecology9.0执行导入流程流程产生的问题
FFMPEG关键结构体——AVFormatContext
MySQL之函数
Analysis of the combination of small program technology advantages and industrial Internet
Key structure of ffmpeg -- AVCodecContext
Spark SQL空值Null,NaN判断和处理
Spark DF增加一列
剖面测量之提取剖面数据
猿桌派第三季开播在即,打开出海浪潮下的开发者新视野
如何制作自己的机器人