zipkin支持GaussDB开发

举报
yd_282553764 发表于 2024/10/17 18:00:53 2024/10/17
【摘要】 了解Zipkin支持GaussDB存储的开发流程

1. 什么是 Zipkin?

Zipkin 是一个分布式追踪系统,旨在帮助开发人员跟踪并优化微服务架构中的请求流程。在一个微服务系统中,通常一个用户请求会触发多个服务之间的交互,而 Zipkin 能够记录和展示这些服务的调用链路,帮助开发人员快速定位性能瓶颈或错误。

Zipkin 的核心功能包括:

收集:从多个服务中收集追踪数据,这些数据可以是从服务启动到结束的调用、异常等。

存储:将追踪数据存储在数据库中,便于后续分析。

查询:用户可以通过 Zipkin 提供的 Web UI 查询特定的追踪记录。

可视化:Zipkin 提供了用户友好的可视化界面,展示服务调用链路以及各个节点的耗时和状态。

基本上所有的分布式调用链系统,都会包括这四个组件

2. Zipkin 的架构与组件流程

Zipkin 的架构由多个关键组件组成,负责数据收集、存储和展示。以下是 Zipkin 的核心组件及其工作流程:

Collector (收集器):负责接收从不同服务发送过来的追踪数据。这些数据通过 HTTP 或 Kafka 等传输方式进入 Zipkin 系统。

Storage (存储):Zipkin 支持多种存储后端,包括 Elasticsearch、Cassandra、MySQL 等。存储组件负责将收集到的追踪数据持久化,便于后续查询。

Query (查询):通过该组件,用户可以根据时间、服务名、操作名等条件,查询到特定的追踪信息。查询结果由 Web UI 显示。

Web UI:这是 Zipkin 提供的用户界面,用于可视化展示服务调用链路及其详细信息,帮助用户分析和定位问题。

3. Zipkin Client 和 Server 的通信数据结构

Zipkin 客户端传递给 Zipkin Server 的数据是符合 OpenTracing 标准的,它遵循一种通用的分布式追踪数据格式,主要是以 JSON 的形式发送 Span 数据。每个 Span 描述一个分布式追踪中的独立操作,多个 Span 组成了一个完整的 Trace

traceIdTrace 的唯一标识符。所有属于同一请求的 Span 会共享相同的 traceId

id:当前 Span 的唯一标识符。每个 Span 有自己独立的 id

name:表示操作的名称,通常为 HTTP 方法和路径,例如 "get /api"

timestamp:当前 Span 开始的时间戳,单位是微秒。

durationSpan 持续时间,单位是微秒。

localEndpoint:当前服务的信息(例如本地服务名称、IP 地址、端口)。通常用于标识 Span 属于哪个微服务。

remoteEndpoint:远程调用服务的信息(例如目标服务名称、IP 地址、端口)。表示该 Span 的远程依赖。

tags:键值对的形式,标识关于这个 Span 的一些额外元数据,例如 HTTP 方法、路径等。

annotations:时间戳注解,用于标识特定事件。例如 cs (client send) 和 cr (client receive) 分别表示客户端发送和接收到响应的时间。

parentId:标识当前 Span 的父级 Span。如果某个 Span 是由其他操作(Span)引发的,那么这个字段用于表示它的父操作。

kind:表示当前 Span 的角色。通常可以是 CLIENTSERVER,分别代表客户端发起的调用和服务器接收到的调用。

[
  {
    "traceId": "4bf92f3577b34da6a3ce929d0e0e4736",
    "id": "b2a4f8f7a5d5a9fd",
    "name": "get /api",
    "timestamp": 1633028452000000,
    "duration": 150000,
    "localEndpoint": {
      "serviceName": "user-service",
      "ipv4": "192.168.1.5",
      "port": 8080
    },
    "remoteEndpoint": {
      "serviceName": "auth-service",
      "ipv4": "192.168.1.6",
      "port": 8081
    },
    "tags": {
      "http.method": "GET",
      "http.path": "/api"
    },
    "annotations": [
      {
        "timestamp": 1633028452000000,
        "value": "cs"
      },
      {
        "timestamp": 1633028452150000,
        "value": "cr"
      }
    ],
    "parentId": "b2a4f8f7a5d5a8bb",
    "kind": "SERVER"
  }
]

4. Zipkin存储GaussDB的步骤

在 Zipkin 的源码中,如果要为 GaussDB 添加数据库存储类型并配置存储支持,主要是两步:存储类型的定义存储配置的实现。

1. 新建仓库地址

首先fork zipkin(https://github.com/openzipkin/zipkin)的仓库地址,并在master上新建分支。

2. 在源码中添加 GaussDB 存储类型

Zipkin 的存储类型是在 zipkin-server 项目中配置的,通常通过 Spring 配置来选择存储类型。你可以将 GaussDB 作为一个新的存储选项添加到现有的存储类型中。

步骤:

添加 ZipkinGaussDBStorageConfiguration

以MySQL为例,在 Zipkin Server 中,存储配置主要是在 ZipkinMySQLStorageConfiguration 中进行的(路径为 zipkin2.server.internal.mysql.ZipkinMySQLStorageConfiguration)。

2.1. 新建 ZipkinGaussDBStorageConfiguration.java 文件。

2.2. @Conditional 配置中,为 GaussDB 添加一个新的条件配置。例如,可以参考以下的 MySQL 的实现:

@EnableConfigurationProperties(ZipkinMySQLStorageProperties.class)
@ConditionalOnClass(MySQLStorage.class)
@ConditionalOnProperty(name = "zipkin.storage.type", havingValue = "mysql")
@ConditionalOnMissingBean(StorageComponent.class)
@Import(ZipkinSelfTracingMySQLStorageConfiguration.class)
public class ZipkinMySQLStorageConfiguration {
}

修改@ConditionalOnProperty(name = "zipkin.storage.type", havingValue = "mysql") 为@ConditionalOnProperty(name = "zipkin.storage.type", havingValue = "gaussdb")

将ZipkinMySQLStorageProperties的调整为ZipkinGaussDBStorageProperties

2.3. 配置bean,参考以下的mysql

@Bean StorageComponent storage(
    Executor mysqlExecutor,
    DataSource mysqlDataSource,
    @Value("${zipkin.storage.strict-trace-id:true}") boolean strictTraceId,
    @Value("${zipkin.storage.search-enabled:true}") boolean searchEnabled,
    @Value("${zipkin.storage.autocomplete-keys:}") List<String> autocompleteKeys) {
    return MySQLStorage.newBuilder()
      .strictTraceId(strictTraceId)
      .searchEnabled(searchEnabled)
      .autocompleteKeys(autocompleteKeys)
      .executor(mysqlExecutor)
      .datasource(mysqlDataSource)
      .listenerProvider(mysqlListener)
      .build();
  }

这里要建立一个StorageComponent的bean。StorageComponent是zipkin的存储和查询的接口。

关于strictTraceId

Trace ID 是分布式追踪系统中的一个唯一标识符,用于跟踪一次完整的请求链路。这个 Trace ID 在分布式系统中是通过不同的微服务传递的,以记录每个服务处理的相关 Span

128 位 Trace ID:Zipkin 支持生成和使用 128 位长度的 Trace ID,这是一个标准长度,用于确保全球唯一性和避免冲突。

64 位 Trace ID:为了向后兼容,Zipkin 也支持 64 位的 Trace ID,即较短的 Trace ID。有些老旧系统或库可能只生成 64 位的 Trace ID

strictTraceId 的作用是让你控制 Zipkin 是否要求所有传入的 Trace ID 必须是严格的 128 位。

关于autocompleteKeys

Zipkin 中,用于指定需要在存储后端中启用自动补全功能的标签键(tags)。该功能可以帮助用户在查询追踪数据时,通过自动补全方式快速定位特定的 tags 值。

3. 实现GaussDbStorage

public final class GaussDbStorage extends StorageComponent {
  // JDBC 数据库连接、配置等
  final DataSource dataSource;

  public GaussDbStorage(DataSource dataSource) {
    this.dataSource = dataSource;
  }

  @Override
  public SpanConsumer spanConsumer() {
    // 实现 span 存储逻辑
    return new GaussDbSpanConsumer(dataSource);
  }

  @Override
  public SpanStore spanStore() {
    // 实现 span 查询逻辑
    return new GaussDbSpanStore(dataSource);
  }

  @Override
  public CheckResult check() {
    // 实现数据库连接检查
    try (Connection conn = dataSource.getConnection()) {
      return CheckResult.OK;
    } catch (Exception e) {
      return CheckResult.failed(e);
    }
  }
}

实现存储逻辑:实现 SpanConsumerSpanStore两个核心类SpanConsumer实现Span 数据插入到 GaussDB 中,SpanStore实现查询逻辑。

配置支持:通过配置文件为 GaussDB 提供连接信息,并使用 Spring 自动配置 DataSource。

4 提交 PR 到上流仓库

使用git 提交规范进行提交,可以参考我的文章:https://bbs.huaweicloud.com/blogs/436866

在 GitHub 上打开你的 Fork 仓库,找到你的分支,点击 “New Pull Request” 按钮,选择与上流仓库进行对比并提交。

在 PR 中,请确保提供详细的描述,说明我们所做的改动、功能实现、如何测试等信息,以便维护者能够快速理解并审核你的代码。

【声明】本内容来自华为云开发者社区博主,不代表华为云及华为云开发者社区的观点和立场。转载时必须标注文章的来源(华为云社区)、文章链接、文章作者等基本信息,否则作者和本社区有权追究责任。如果您发现本社区中有涉嫌抄袭的内容,欢迎发送邮件进行举报,并提供相关证据,一经查实,本社区将立刻删除涉嫌侵权内容,举报邮箱: cloudbbs@huaweicloud.com
  • 点赞
  • 收藏
  • 关注作者

评论(0

0/1000
抱歉,系统识别当前为高风险访问,暂不支持该操作

全部回复

上滑加载中

设置昵称

在此一键设置昵称,即可参与社区互动!

*长度不超过10个汉字或20个英文字符,设置后3个月内不可修改。

*长度不超过10个汉字或20个英文字符,设置后3个月内不可修改。