Google Dapper学习

1 . 介绍

1.1 产生背景

以一次网络搜索为例,用户在Google首页输入关键字后只要敲个回车键就能返回搜索结果。但是这样一个简单的请求可能会经过多个子系统的处理,而且这些处理是发生在不同机器甚至是不同集群上的。

同时在网络搜索过程中用户对请求延迟敏感度非常高,所以快速定位到是哪个子系统、哪个环节出问题是非常重要的。

 

1.2 Dapper设计目标

两个重要的需求需要予以满足:

  • 全面(ubiquitous deployment):追踪系统的监控对象应该是没有死角的

  • 持续(continuous monitoring):异常的发生是无法预料的,而且可能是很难复现的

 

基于此Dapper有三个最重要的设计目标

  • 低开销(Low overhead):dapper本质是用来发现性能消耗问题,不能因为引入dapper而带来过度开销

  • 低侵入(Application-level transparency):应用级透明,使用者可以无需显式嵌入dapper相关代码,否则会对代码维护和职责划分带来麻烦

  • 高扩展(Scalability):至少未来几年的服务和集群的扩展,跟踪系统应该具有相关的扩展性能够适应。

 

2. 实现简介

2.1 如何跟踪

利用应用程序或中间件给每条记录一个全局标志符,借此将一串请求关联起来。

 

2.1.1 数据格式

Dapper用span来表示一个服务调用开始和结束的时间,对于Dapper来说,一个trace(跟踪过程)实际上是一颗树,树中的节点被称为一个span,根节点被称为root span。

 

2.1.2 数据存储

Dapper的整个数据收集过程如下图所示:首先将span数据写入本地日志文件,然后将数据收集并写入Bigtable。

每个trace记录将会被作为表中的一行,Bigtable的稀疏表结构非常适合存储trace记录,因为每条记录可能有任意个的span。

2.2 低开销

2.2.1 成本损耗

跟踪系统的成本由两部分组成

  • 生成追踪和收集追踪数据

  • 存储和分析跟踪数据

 

生成:

生成跟踪的开销是Dapper性能影响中最关键的部分,Dapper运行库中最重要的跟踪生成消耗在于创建和销毁span和annotation,并记录到本地磁盘供后续的收集。根span的创建和销毁需要损耗平均204纳秒的时间,而同样的操作在其他span上需要消耗176纳秒。时间上的差别主要在于需要在跟span上给这次跟踪分配一个全局唯一的ID。

 

存储:

在Dapper运行期写入到本地磁盘是最昂贵的操作,但是他们的可见损耗大大减少,因为写入日志文件和操作相对于被跟踪的应用系统来说都是异步的。不过,日志写入的操作如果在大流量的情况,尤其是每一个请求都被跟踪的情况下就会变得可以察觉到。

收集:

在生产环境下,跟踪数据处理中,这个守护进程从来没有超过0.3%的单核cpu使用率,而且只有很少量的内存使用(以及堆碎片的噪音)。我们还限制了Dapper守护进程为内核scheduler最低的优先级,以防在一台高负载的服务器上发生cpu竞争。

2.2.2 可变采样

可以不记录全部请求,而通过采样的方式来尽可能降低开销(定位耗时问题点时适用,全面跟踪系统追溯问题时不适用)

Dapper的第一个版本设置了一个统一的采样率1/1024,也就是1024个请求才追踪一次。后来发现对一些高吞吐的服务来说是可以的,比如每秒几十万的请求,但是对一些低吞吐量的服务,比如每秒几十个请求的服务,如果采样率设置为1/1024,很多性能问题可能不会被追踪到。因此在第二版本dapper提供了自适应的采样率,在低吞吐量时候提高采样率,在高吞吐量时降低采样率。

2.3 低侵入

在Google,应用使用的是相同的多线程,控制流,RPC等基础库代码,所以仅通过修改它们就可以实现跟踪功能。通过底层中间件支持来实现对业务代码低侵入。

2.3.1 异步处理

当线程进行一个被跟踪的处理时,Dapper会将一个trace context关联到线程本地化存储中。trace context中包含了span相关属性,比如trace和span id。

对于需要进行异步处理的情况,Google开发者通常都会采用一个通用的控制流库来实现回调,并将它们调度到一个线程池或是执行器中调用。Dapper保证所有回调都会保存它们创建者的trace context,同时在该回调被调用时该trace context也会被关联到对应线程。这样,Dapper就可以实现这种异步处理过程的跟踪。

2.4 企业级应用

工具

介绍

Zipkin —— twitter

https://zipkin.apache.org/

https://github.com/openzipkin/zipkin

hydra —— 京东

https://github.com/odenny/hydra

6年前更新

鹰眼 —— 阿里

 

 

 

3. 一点思考

3.1.1 耗时定位粒度

理论可以定位到方法级别

但是耗时长原因很多,不一定是方法耗时长,比如说请求在线程池中等待,根据这种统计耗时方式,可能不能快速定位到问题(mtthrift在1.8.5.10版本中,服务端在cat上打点耗时统计是没有包含在线程池中等待的时间的,也就是说从服务端的cat统计来看mtthrift请求耗时,可以看到一个请求在服务端处理完成的真实需要花费的时间)

 

4.博客

https://blog.csdn.net/zhanlijun/article/details/13169771

https://www.cnblogs.com/rongfengliang/p/6209301.html

https://www.jianshu.com/p/7c719a75df8c

https://blog.csdn.net/liumiaocn/article/details/80657661

Guess you like

Origin blog.csdn.net/maoyeqiu/article/details/116156625