【Dubbo】Dubbo简单自定义链路传递traceId

2024-04-22 02:52

本文主要是介绍【Dubbo】Dubbo简单自定义链路传递traceId,希望对大家解决编程问题提供一定的参考价值,需要的开发者们随着小编来一起学习吧!

需求

因为服务器内存不足,没有引入链路追踪的框架,项目使用到了Dubbo,所有通过self4j的MDC和Dubbo的RpcContext实现简单的traceId 的多服务模块的传递

解决思路

  1. 在第一个模块生成traceId(比如网关模块),生成traceId,并存入MDC,RpcContext,请求头等地方,使用完在响应时进行删除
  2. 如果是Dubbo的Rpc调用则能将traceId传递到服务提供者模块,服务端通过过滤器进行拦截,加入到自己的MDC,RpcContext,使用完后清除
  3. 如果是网关的转发请求,则通过请求头进行转发traceId,下游模块存入自己的MDC,RpcContext,使用完后清除
  4. 因为Dubbo的RpcContext每次调用服务端方法后,消费端的RpcContext就会被清除,所有通过MDC在每次rpc调用前通过调用前过滤器再加上traceId

版本

        <dependency><groupId>org.apache.dubbo</groupId><artifactId>dubbo</artifactId><version>3.1.6</version></dependency>

解决方案

Dubbo消费端过滤器

就是调用服务器提供者的接口前,在消费端先过滤,加一点参数啥的,再转发

以下默认已经配置好,并写好了Dubbo远程调用服务,并能够进行调用。在此基础上进行过滤器添加。

1 . 代码

@Activate(group = {CommonConstants.CONSUMER}, order = -30000)
@Slf4j
public class RemoteTraceIdFilter implements Filter {private static final String TRACE_ID = "traceId";@Overridepublic Result invoke(Invoker<?> invoker, Invocation invocation) throws RpcException {// 消费者RpcServiceContext currentServiceContext = RpcContext.getCurrentServiceContext();boolean consumerSide = currentServiceContext.isConsumerSide();if (consumerSide) {String traceId = MDC.get(TRACE_ID);if(traceId==null){traceId = UUID.randomUUID().toString();}//消费者 将trace_id(业务流水号) set至上下文中RpcContext.getClientAttachment().setAttachment(TRACE_ID, traceId);} else {// 服务提供者
//            String traceId = RpcContext.getClientAttachment().getAttachment(TRACE_ID);String traceId = RpcContext.getServerAttachment().getAttachment(TRACE_ID);if (traceId == null) {traceId = UUID.randomUUID().toString();}//slf4j 中设置了日志打印格式用作日志链路追踪MDC.put(TRACE_ID, traceId);}try {return invoker.invoke(invocation);} finally {if (RpcContext.getCurrentServiceContext().isProviderSide()) {MDC.remove(TRACE_ID);}else{RpcContext.getClientAttachment().removeAttachment(TRACE_ID);}}}
}
  1. 配置
    在这里插入图片描述1. 创建Resource相关配置(可以参考官方文档 官网)
--META-INF
----dubbo
------org.apache.dubbo.rpc.Filter文件内容(traceId是自定义的,具体看官网)
traceId = 类路径

Dubbo服务提供端过滤器

一个样不赘述

问题

  1. 每次RpcContext中存入值,在过滤器finally都要删除防止内存泄漏
  2. 每次RpcContext中存入值,并调用一次接口后,在消费端再次获取时会获取不到,因为已经被自动删除了,所有此处用了MDC配合RpcContext实现了traceId的保留。
    具体看官网: 链路传递
  3. 侵入性比较高,实现也比较粗糙,如果条件允许建议直接使用sentinel等专业高级好用的框架直接实现链路的追踪

总结

此方式只是一个简单的实现,真实场景允许条件下直接使用sentinel等专门框架完成的限流链路追踪的功能。

这篇关于【Dubbo】Dubbo简单自定义链路传递traceId的文章就介绍到这儿,希望我们推荐的文章对编程师们有所帮助!



http://www.chinasem.cn/article/924658

相关文章

SpringBoot 异常处理/自定义格式校验的问题实例详解

《SpringBoot异常处理/自定义格式校验的问题实例详解》文章探讨SpringBoot中自定义注解校验问题,区分参数级与类级约束触发的异常类型,建议通过@RestControllerAdvice... 目录1. 问题简要描述2. 异常触发1) 参数级别约束2) 类级别约束3. 异常处理1) 字段级别约束

Java中使用 @Builder 注解的简单示例

《Java中使用@Builder注解的简单示例》@Builder简化构建但存在复杂性,需配合其他注解,导致可变性、抽象类型处理难题,链式编程非最佳实践,适合长期对象,避免与@Data混用,改用@G... 目录一、案例二、不足之处大多数同学使用 @Builder 无非就是为了链式编程,然而 @Builder

SpringBoot整合Dubbo+ZK注册失败的坑及解决

《SpringBoot整合Dubbo+ZK注册失败的坑及解决》使用Dubbo框架时,需在公共pom添加依赖,启动类加@EnableDubbo,实现类用@DubboService替代@Service,配... 目录1.先看下公共的pom(maven创建的pom工程)2.启动类上加@EnableDubbo3.实

Spring boot整合dubbo+zookeeper的详细过程

《Springboot整合dubbo+zookeeper的详细过程》本文讲解SpringBoot整合Dubbo与Zookeeper实现API、Provider、Consumer模式,包含依赖配置、... 目录Spring boot整合dubbo+zookeeper1.创建父工程2.父工程引入依赖3.创建ap

SpringBoot+EasyExcel实现自定义复杂样式导入导出

《SpringBoot+EasyExcel实现自定义复杂样式导入导出》这篇文章主要为大家详细介绍了SpringBoot如何结果EasyExcel实现自定义复杂样式导入导出功能,文中的示例代码讲解详细,... 目录安装处理自定义导出复杂场景1、列不固定,动态列2、动态下拉3、自定义锁定行/列,添加密码4、合并

Java实现自定义table宽高的示例代码

《Java实现自定义table宽高的示例代码》在桌面应用、管理系统乃至报表工具中,表格(JTable)作为最常用的数据展示组件,不仅承载对数据的增删改查,还需要配合布局与视觉需求,而JavaSwing... 目录一、项目背景详细介绍二、项目需求详细介绍三、相关技术详细介绍四、实现思路详细介绍五、完整实现代码

一文详解Java Stream的sorted自定义排序

《一文详解JavaStream的sorted自定义排序》Javastream中的sorted方法是用于对流中的元素进行排序的方法,它可以接受一个comparator参数,用于指定排序规则,sorte... 目录一、sorted 操作的基础原理二、自定义排序的实现方式1. Comparator 接口的 Lam

使用Python进行GRPC和Dubbo协议的高级测试

《使用Python进行GRPC和Dubbo协议的高级测试》GRPC(GoogleRemoteProcedureCall)是一种高性能、开源的远程过程调用(RPC)框架,Dubbo是一种高性能的分布式服... 目录01 GRPC测试安装gRPC编写.proto文件实现服务02 Dubbo测试1. 安装Dubb

基于Python实现一个简单的题库与在线考试系统

《基于Python实现一个简单的题库与在线考试系统》在当今信息化教育时代,在线学习与考试系统已成为教育技术领域的重要组成部分,本文就来介绍一下如何使用Python和PyQt5框架开发一个名为白泽题库系... 目录概述功能特点界面展示系统架构设计类结构图Excel题库填写格式模板题库题目填写格式表核心数据结构

如何自定义一个log适配器starter

《如何自定义一个log适配器starter》:本文主要介绍如何自定义一个log适配器starter的问题,具有很好的参考价值,希望对大家有所帮助,如有错误或未考虑完全的地方,望不吝赐教... 目录需求Starter 项目目录结构pom.XML 配置LogInitializer实现MDCInterceptor