--- layout: post title: 17.hadoop-2.7.2官网文档翻译-实现Hadoop中Dapper-like追踪 category: 技术 tags: Hadoop keywords: description: 实现Hadoop中Dapper-like追踪。官网地址为:http://hadoop.apache.org/docs/r2.7.2/hadoop-project-dist/hadoop-common/Tracing.html --- {:toc} ## Hadoop中Dapper-like追踪 ### HTrace [HDFS-5274](https://issues.apache.org/jira/browse/HDFS-5274){:target="_blank"} 添加了通过HDFS跟踪请求的支持,使用的开源的跟踪库[ Apache HTrace](https://git-wip-us.apache.org/repos/asf/incubator-htrace.git){:target="_blank"}, 设置跟踪是很简单的,但它需要对你的客户端代码做很小的修改。 ### 采样器 使用`core-site.xml`属性`hadoop.htrace.sampler`配置采样器。值可以是`NeverSampler`, `AlwaysSampler` 或 `ProbabilitySampler`。 NeverSampler: HTrace 一直是关闭的; AlwaysSampler:HTrace一直是开启的; ProbabilitySampler: HTrace在最高级别持续时间的一定百分比是开启的。 ```xml hadoop.htrace.sampler NeverSampler ``` ### SpanReceiver 追踪系统的工作是收集结构叫做“Spans”的信息。通过实现SpanReceiver接口,由你决定选择你想怎样接收该信息。 这是定义的一个方法:`public void receiveSpan(Span span);`。 在`core-site.xml`属性`hadoop.htrace.spanreceiver.classes`中通过用逗号分隔的继承SpanReceiver接口的类的全类名配置你想用的SpanReceivers。 ```xml hadoop.htrace.spanreceiver.classes org.apache.htrace.impl.LocalFileSpanReceiver hadoop.htrace.local-file-span-receiver.path /var/log/hadoop/htrace.out ``` 如果你使用HTrace附带的span receiver,可以省略前缀包名: ```xml hadoop.htrace.spanreceiver.classes LocalFileSpanReceiver ``` ### 设置ZipkinSpanReceiver 你可以使用`ZipkinSpanReceiver`(使用[Zipkin](https://github.com/twitter/zipkin){:target="_blank"}手机和显示追踪的数据)来替代自己实现SpanReceiver 接口。 为了使用`ZipkinSpanReceiver`,需要先下载并安装[Zipkin](https://github.com/twitter/zipkin){:target="_blank"}。 你也需要将jar包`htrace-zipkin`添加的每个节点的Hadoop类路径下。下面是个例子: ```bash $ git clone https://github.com/cloudera/htrace $ cd htrace/htrace-zipkin $ mvn compile assembly:single $ cp target/htrace-zipkin-*-jar-with-dependencies.jar $HADOOP_HOME/share/hadoop/common/lib/ ``` `ZipkinSpanReceiver`的样板配置如下显示。通过将他们添加到NameNode和DataNode的`core-site.xml`中,`ZipkinSpanReceiver`会在启动时初始化。除了服务端之外,你也需要在客户端添加此配置。 ```xml hadoop.htrace.spanreceiver.classes ZipkinSpanReceiver hadoop.htrace.zipkin.collector-hostname 192.168.1.2 hadoop.htrace.zipkin.collector-port 9410 ``` ### 跟踪配置的动态更新 可以使用`hadoop trace`命令查看和更新每个服务器的追踪配置。你必须通过`-host`选项指定NameNode或DataNode的IPC服务地址。 如果你想更新所有服务器的配置,你需要在所有服务器上运行该命令。 命令`hadoop trace -list`显示与id相关联的已加载的span接收器列表。 ```bash $ hadoop trace -list -host 192.168.56.2:9000 ID CLASS 1 org.apache.htrace.impl.LocalFileSpanReceiver $ hadoop trace -list -host 192.168.56.2:50020 ID CLASS 1 org.apache.htrace.impl.LocalFileSpanReceiver ``` 命令`hadoop trace -remove`从服务器删除span接收器,`-remove`选项将span接受者的id作为参数。 ```bash $ hadoop trace -remove 1 -host 192.168.56.2:9000 Removed trace span receiver 1 ``` 命令`hadoop trace -add`向服务器添加span接受器。需要指定span接收器的类名作为`-class`选项的参数。需要通过`-Cke=value`选项将配置和span接收器关联。 ```bash $ hadoop trace -add -class LocalFileSpanReceiver -Chadoop.htrace.local-file-span-receiver.path=/tmp/htrace.out -host 192.168.56.2:9000 Added trace span receiver 2 with configuration hadoop.htrace.local-file-span-receiver.path = /tmp/htrace.out $ hadoop trace -list -host 192.168.56.2:9000 ID CLASS 2 org.apache.htrace.impl.LocalFileSpanReceiver ``` ### 通过HTrace API开始追踪span 为了追踪,你需要使用tracing span包装追踪逻辑,就像下面展示的。 当最总span运行时,追踪信息通过RPC请求传到服务器。 另外,你需要每次过程都初始化`SpanReceiver`。 ```java import org.apache.hadoop.hdfs.HdfsConfiguration; import org.apache.hadoop.tracing.SpanReceiverHost; import org.apache.htrace.Sampler; import org.apache.htrace.Trace; import org.apache.htrace.TraceScope; //... SpanReceiverHost.getInstance(new HdfsConfiguration()); //... TraceScope ts = Trace.startSpan("Gets", Sampler.ALWAYS); try { ... // traced logic } finally { if (ts != null) ts.close(); } ``` ### 追踪的简单代码 `TracingFsShell.java`展示了Fsshell包装器在调用HDFS的shell命令之前开始追踪span。 ```java import org.apache.hadoop.conf.Configuration; import org.apache.hadoop.fs.FsShell; import org.apache.hadoop.tracing.SpanReceiverHost; import org.apache.hadoop.util.ToolRunner; import org.apache.htrace.Sampler; import org.apache.htrace.Trace; import org.apache.htrace.TraceScope; public class TracingFsShell { public static void main(String argv[]) throws Exception { Configuration conf = new Configuration(); FsShell shell = new FsShell(); conf.setQuietMode(false); shell.setConf(conf); SpanReceiverHost.getInstance(conf); int res = 0; TraceScope ts = null; try { ts = Trace.startSpan("FsShell", Sampler.ALWAYS); res = ToolRunner.run(shell, argv); } finally { shell.close(); if (ts != null) ts.close(); } System.exit(res); } } ``` 可以像下面这样编译并执行代码: ```bash $ javac -cp `hadoop classpath` TracingFsShell.java $ java -cp .:`hadoop classpath` TracingFsShell -ls / ```