首页 > 代码库 > 第二十八章 springboot + zipkin(brave定制-AsyncHttpClient)

第二十八章 springboot + zipkin(brave定制-AsyncHttpClient)

brave本身没有对AsyncHttpClient提供类似于brave-okhttp的ClientRequestInterceptor和ClientResponseInterceptor,所以需要我们定制,而ServerRequestInterceptor和ServerResponseInterceptor是在BraveServletFilter部分直接指定就好了(这在任何client技术下都可以复用)。

实际上,ClientRequestInterceptor和ClientResponseInterceptor也是我们的定制点

 

一、代码

基本参考第二十七章 springboot + zipkin(brave-okhttp实现)

1、service1

1.1、pom.xml

技术分享
 1 <!-- zipkin brave --> 2         <dependency> 3             <groupId>io.zipkin.brave</groupId> 4             <artifactId>brave-core</artifactId> 5             <version>3.9.0</version> 6         </dependency> 7         <dependency> 8             <groupId>io.zipkin.brave</groupId> 9             <artifactId>brave-spancollector-http</artifactId>10             <version>3.9.0</version>11         </dependency>12         <dependency>13             <groupId>io.zipkin.brave</groupId>14             <artifactId>brave-web-servlet-filter</artifactId>15             <version>3.9.0</version>16         </dependency>17         <!-- async-http-client -->18         <dependency>19             <groupId>com.ning</groupId>20             <artifactId>async-http-client</artifactId>21             <version>1.9.31</version>22         </dependency>
View Code

1.2、ZipkinConfig

技术分享
 1 package com.xxx.service1.zipkin.brave.async; 2  3 import org.springframework.context.annotation.Bean; 4 import org.springframework.context.annotation.Configuration; 5  6 import com.github.kristofa.brave.Brave; 7 import com.github.kristofa.brave.EmptySpanCollectorMetricsHandler; 8 import com.github.kristofa.brave.Sampler; 9 import com.github.kristofa.brave.SpanCollector;10 import com.github.kristofa.brave.http.DefaultSpanNameProvider;11 import com.github.kristofa.brave.http.HttpSpanCollector;12 import com.github.kristofa.brave.servlet.BraveServletFilter;13 import com.ning.http.client.AsyncHttpClient;14 15 @Configuration16 public class ZipkinConfig {17     @Bean18     public SpanCollector spanCollector() {19         HttpSpanCollector.Config spanConfig = HttpSpanCollector.Config.builder()20                                               .compressionEnabled(false)//默认false,span在transport之前是否会被gzipped。21                                               .connectTimeout(5000)//5s,默认10s22                                               .flushInterval(1)//1s23                                               .readTimeout(6000)//5s,默认60s24                                               .build();25         return HttpSpanCollector.create("http://localhost:9411", 26                                         spanConfig,27                                         new EmptySpanCollectorMetricsHandler());28     }29 30     @Bean31     public Brave brave(SpanCollector spanCollector) {32         Brave.Builder builder = new Brave.Builder("asyn1 - service1 - 1");//指定serviceName33         builder.spanCollector(spanCollector);34         builder.traceSampler(Sampler.create(1));//采集率35         return builder.build();36     }37 38     @Bean39     public BraveServletFilter braveServletFilter(Brave brave) {40         /**41          * 设置sr、ss拦截器42          */43         return new BraveServletFilter(brave.serverRequestInterceptor(), 44                                       brave.serverResponseInterceptor(),45                                       new DefaultSpanNameProvider());46     }47 48     @Bean49     public AsyncHttpClient asyncHttpClient(){50         return new AsyncHttpClient();51     }52 }
View Code

说明:指定了serviceName:"asyn1 - service1 - 1"

1.3、ZipkinAsyncController

技术分享
 1 package com.xxx.service1.zipkin.brave.async; 2  3 import java.net.URI; 4 import java.util.concurrent.Future; 5  6 import org.springframework.beans.factory.annotation.Autowired; 7 import org.springframework.web.bind.annotation.RequestMapping; 8 import org.springframework.web.bind.annotation.RequestMethod; 9 import org.springframework.web.bind.annotation.RestController;10 11 import com.github.kristofa.brave.Brave;12 import com.github.kristofa.brave.http.DefaultSpanNameProvider;13 import com.github.kristofa.brave.http.HttpClientRequest;14 import com.github.kristofa.brave.http.HttpClientRequestAdapter;15 import com.github.kristofa.brave.http.HttpClientResponseAdapter;16 import com.github.kristofa.brave.http.HttpResponse;17 import com.ning.http.client.AsyncHttpClient;18 import com.ning.http.client.Request;19 import com.ning.http.client.RequestBuilder;20 import com.ning.http.client.Response;21 22 import io.swagger.annotations.Api;23 import io.swagger.annotations.ApiOperation;24 25 @Api("zipkin brave async api")26 @RestController27 @RequestMapping("/zipkin/async/service1")28 public class ZipkinAsyncController {29 30     @Autowired31     private AsyncHttpClient asyncHttpClient;32     @Autowired33     private Brave           brave;34 35     @ApiOperation("trace第一步")36     @RequestMapping(value = "http://www.mamicode.com/test1", method = RequestMethod.GET)37     public String myboot() {38 39         try {40             RequestBuilder builder = new RequestBuilder();41             String url = "http://localhost:8032/zipkin/async/service2/test2";42             builder.setUrl(url);43             Request request = builder.build();44 45             clientRequestInterceptor(request);46             Future<Response> response = asyncHttpClient.executeRequest(request);47             clientResponseInterceptor(response.get());48 49             return response.get().getResponseBody();50         } catch (Exception e) {51             e.printStackTrace();52             return "";53         }54     }55 56     private void clientRequestInterceptor(Request request) {57         brave.clientRequestInterceptor().handle(new HttpClientRequestAdapter(new HttpClientRequest() {58 59             @Override60             public URI getUri() {61                 return URI.create(request.getUrl());62             }63 64             @Override65             public String getHttpMethod() {66                 return request.getMethod();67             }68 69             @Override70             public void addHeader(String headerKey, String headerValue) {71                 request.getHeaders().add(headerKey, headerValue);72             }73         }, new DefaultSpanNameProvider()));74     }75 76     private void clientResponseInterceptor(Response response) {77         brave.clientResponseInterceptor().handle(new HttpClientResponseAdapter(new HttpResponse() {78             public int getHttpStatusCode() {79                 return response.getStatusCode();80             }81         }));82     }83 84 }
View Code

说明:

  • clientRequestInterceptor(com.ning.http.client.Request request)
    • 其实就是在做cs
  • clientResponseInterceptor(com.ning.http.client.Response response)
    • 其实就是在做cr

 

2、service2

2.1、pom.xml

技术分享
 1 <!-- zipkin brave --> 2         <dependency> 3             <groupId>io.zipkin.brave</groupId> 4             <artifactId>brave-core</artifactId> 5             <version>3.9.0</version> 6         </dependency> 7         <dependency> 8             <groupId>io.zipkin.brave</groupId> 9             <artifactId>brave-spancollector-http</artifactId>10             <version>3.9.0</version>11         </dependency>12         <dependency>13             <groupId>io.zipkin.brave</groupId>14             <artifactId>brave-web-servlet-filter</artifactId>15             <version>3.9.0</version>16         </dependency>17         <!-- async-http-client -->18         <dependency>19             <groupId>com.ning</groupId>20             <artifactId>async-http-client</artifactId>21             <version>1.9.31</version>22         </dependency>
View Code

2.2、ZipkinConfig

技术分享
 1 package com.xxx.service1.zipkin.brave.async; 2  3 import org.springframework.context.annotation.Bean; 4 import org.springframework.context.annotation.Configuration; 5  6 import com.github.kristofa.brave.Brave; 7 import com.github.kristofa.brave.EmptySpanCollectorMetricsHandler; 8 import com.github.kristofa.brave.Sampler; 9 import com.github.kristofa.brave.SpanCollector;10 import com.github.kristofa.brave.http.DefaultSpanNameProvider;11 import com.github.kristofa.brave.http.HttpSpanCollector;12 import com.github.kristofa.brave.servlet.BraveServletFilter;13 import com.ning.http.client.AsyncHttpClient;14 15 @Configuration16 public class ZipkinConfig {17     @Bean18     public SpanCollector spanCollector() {19         HttpSpanCollector.Config spanConfig = HttpSpanCollector.Config.builder()20                                               .compressionEnabled(false)//默认false,span在transport之前是否会被gzipped。21                                               .connectTimeout(5000)//5s,默认10s22                                               .flushInterval(1)//1s23                                               .readTimeout(6000)//5s,默认60s24                                               .build();25         return HttpSpanCollector.create("http://localhost:9411", 26                                         spanConfig,27                                         new EmptySpanCollectorMetricsHandler());28     }29 30     @Bean31     public Brave brave(SpanCollector spanCollector) {32         Brave.Builder builder = new Brave.Builder("asyn2 - service2 - 2");//指定serviceName33         builder.spanCollector(spanCollector);34         builder.traceSampler(Sampler.create(1));//采集率35         return builder.build();36     }37 38     @Bean39     public BraveServletFilter braveServletFilter(Brave brave) {40         /**41          * 设置sr、ss拦截器42          */43         return new BraveServletFilter(brave.serverRequestInterceptor(), 44                                       brave.serverResponseInterceptor(),45                                       new DefaultSpanNameProvider());46     }47 48     @Bean49     public AsyncHttpClient asyncHttpClient(){50         return new AsyncHttpClient();51     }52 }
View Code

说明:指定了serviceName:"asyn2 - service2 - 2"

2.3、ZipkinAsyncController

技术分享
 1 package com.xxx.service2.zipkin.brave.async; 2  3 import java.net.URI; 4 import java.util.concurrent.Future; 5  6 import org.springframework.beans.factory.annotation.Autowired; 7 import org.springframework.web.bind.annotation.RequestMapping; 8 import org.springframework.web.bind.annotation.RequestMethod; 9 import org.springframework.web.bind.annotation.RestController;10 11 import com.github.kristofa.brave.Brave;12 import com.github.kristofa.brave.http.DefaultSpanNameProvider;13 import com.github.kristofa.brave.http.HttpClientRequest;14 import com.github.kristofa.brave.http.HttpClientRequestAdapter;15 import com.github.kristofa.brave.http.HttpClientResponseAdapter;16 import com.github.kristofa.brave.http.HttpResponse;17 import com.ning.http.client.AsyncHttpClient;18 import com.ning.http.client.Request;19 import com.ning.http.client.RequestBuilder;20 import com.ning.http.client.Response;21 22 import io.swagger.annotations.Api;23 import io.swagger.annotations.ApiOperation;24 25 @Api("zipkin brave async api")26 @RestController27 @RequestMapping("/zipkin/async/service2")28 public class ZipkinAsyncController {29 30     @Autowired31     private AsyncHttpClient asyncHttpClient;32     @Autowired33     private Brave           brave;34 35     @ApiOperation("trace第2步")36     @RequestMapping(value = "http://www.mamicode.com/test2", method = RequestMethod.GET)37     public String myboot2() {38 39         try {40             /*****************************serivce3*******************************/41             RequestBuilder builder3 = new RequestBuilder();42             String url3 = "http://localhost:8033/zipkin/async/service3/test3";43             builder3.setUrl(url3);44             Request request3 = builder3.build();45 46             clientRequestInterceptor(request3);47             Future<Response> response3 = asyncHttpClient.executeRequest(request3);48             clientResponseInterceptor(response3.get());49 50             /*****************************serivce4*******************************/51             RequestBuilder builder4 = new RequestBuilder();52             String url4 = "http://localhost:8034/zipkin/async/service4/test4";53             builder4.setUrl(url4);54             Request request4 = builder4.build();55 56             clientRequestInterceptor(request4);57             Future<Response> response4 = asyncHttpClient.executeRequest(request4);58             clientResponseInterceptor(response4.get());59 60             return response3.get().getResponseBody() + "=====" + response4.get().getResponseBody();61         } catch (Exception e) {62             e.printStackTrace();63             return "";64         }65     }66 67     private void clientRequestInterceptor(Request request) {68         brave.clientRequestInterceptor().handle(new HttpClientRequestAdapter(new HttpClientRequest() {69 70             @Override71             public URI getUri() {72                 return URI.create(request.getUrl());73             }74 75             @Override76             public String getHttpMethod() {77                 return request.getMethod();78             }79 80             @Override81             public void addHeader(String headerKey, String headerValue) {82                 request.getHeaders().add(headerKey, headerValue);83             }84         }, new DefaultSpanNameProvider()));85     }86 87     private void clientResponseInterceptor(Response response) {88         brave.clientResponseInterceptor().handle(new HttpClientResponseAdapter(new HttpResponse() {89             public int getHttpStatusCode() {90                 return response.getStatusCode();91             }92         }));93     }94 95 }
View Code

 

3、service3

3.1、pom.xml

技术分享
 1 <!-- zipkin brave --> 2         <dependency> 3             <groupId>io.zipkin.brave</groupId> 4             <artifactId>brave-core</artifactId> 5             <version>3.9.0</version> 6         </dependency> 7         <dependency> 8             <groupId>io.zipkin.brave</groupId> 9             <artifactId>brave-spancollector-http</artifactId>10             <version>3.9.0</version>11         </dependency>12         <dependency>13             <groupId>io.zipkin.brave</groupId>14             <artifactId>brave-web-servlet-filter</artifactId>15             <version>3.9.0</version>16         </dependency>
View Code

3.2、ZipkinConfig

技术分享
 1 package com.xxx.service3.zipkin.brave.async; 2  3 import org.springframework.context.annotation.Bean; 4 import org.springframework.context.annotation.Configuration; 5  6 import com.github.kristofa.brave.Brave; 7 import com.github.kristofa.brave.EmptySpanCollectorMetricsHandler; 8 import com.github.kristofa.brave.Sampler; 9 import com.github.kristofa.brave.SpanCollector;10 import com.github.kristofa.brave.http.DefaultSpanNameProvider;11 import com.github.kristofa.brave.http.HttpSpanCollector;12 import com.github.kristofa.brave.servlet.BraveServletFilter;13 14 @Configuration15 public class ZipkinConfig {16     @Bean17     public SpanCollector spanCollector() {18         HttpSpanCollector.Config spanConfig = HttpSpanCollector.Config.builder()19                                               .compressionEnabled(false)//默认false,span在transport之前是否会被gzipped。20                                               .connectTimeout(5000)//5s,默认10s21                                               .flushInterval(1)//1s22                                               .readTimeout(6000)//5s,默认60s23                                               .build();24         return HttpSpanCollector.create("http://localhost:9411", 25                                         spanConfig,26                                         new EmptySpanCollectorMetricsHandler());27     }28 29     @Bean30     public Brave brave(SpanCollector spanCollector) {31         Brave.Builder builder = new Brave.Builder("asyn3 - service3 - 3");//指定serviceName32         builder.spanCollector(spanCollector);33         builder.traceSampler(Sampler.create(1));//采集率34         return builder.build();35     }36 37     @Bean38     public BraveServletFilter braveServletFilter(Brave brave) {39         /**40          * 设置sr、ss拦截器41          */42         return new BraveServletFilter(brave.serverRequestInterceptor(), 43                                       brave.serverResponseInterceptor(),44                                       new DefaultSpanNameProvider());45     }46 }
View Code

说明:指定了serviceName:"asyn3 - service3 - 3" 

3.3、ZipkinAsyncController

技术分享
 1 package com.xxx.service3.zipkin.brave.async; 2  3 import org.springframework.web.bind.annotation.RequestMapping; 4 import org.springframework.web.bind.annotation.RequestMethod; 5 import org.springframework.web.bind.annotation.RestController; 6  7 import io.swagger.annotations.Api; 8 import io.swagger.annotations.ApiOperation; 9 10 @Api("zipkin brave async api")11 @RestController12 @RequestMapping("/zipkin/async/service3")13 public class ZipkinAsyncController {14 15     @ApiOperation("trace第3步")16     @RequestMapping(value = "http://www.mamicode.com/test3", method = RequestMethod.GET)17     public String myboot3() {18 19         try {20             return "async - service3";21         } catch (Exception e) {22             e.printStackTrace();23             return "";24         }25     }26 27 }
View Code

 

4、service4

4.1、pom.xml

技术分享
 1 <!-- zipkin brave --> 2         <dependency> 3             <groupId>io.zipkin.brave</groupId> 4             <artifactId>brave-core</artifactId> 5             <version>3.9.0</version> 6         </dependency> 7         <dependency> 8             <groupId>io.zipkin.brave</groupId> 9             <artifactId>brave-spancollector-http</artifactId>10             <version>3.9.0</version>11         </dependency>12         <dependency>13             <groupId>io.zipkin.brave</groupId>14             <artifactId>brave-web-servlet-filter</artifactId>15             <version>3.9.0</version>16         </dependency>
View Code

4.2、ZipkinConfig

技术分享
 1 package com.xxx.service4.zipkin.brave.async; 2  3 import org.springframework.context.annotation.Bean; 4 import org.springframework.context.annotation.Configuration; 5  6 import com.github.kristofa.brave.Brave; 7 import com.github.kristofa.brave.EmptySpanCollectorMetricsHandler; 8 import com.github.kristofa.brave.Sampler; 9 import com.github.kristofa.brave.SpanCollector;10 import com.github.kristofa.brave.http.DefaultSpanNameProvider;11 import com.github.kristofa.brave.http.HttpSpanCollector;12 import com.github.kristofa.brave.servlet.BraveServletFilter;13 14 @Configuration15 public class ZipkinConfig {16     @Bean17     public SpanCollector spanCollector() {18         HttpSpanCollector.Config spanConfig = HttpSpanCollector.Config.builder()19                                               .compressionEnabled(false)//默认false,span在transport之前是否会被gzipped。20                                               .connectTimeout(5000)//5s,默认10s21                                               .flushInterval(1)//1s22                                               .readTimeout(6000)//5s,默认60s23                                               .build();24         return HttpSpanCollector.create("http://localhost:9411", 25                                         spanConfig,26                                         new EmptySpanCollectorMetricsHandler());27     }28 29     @Bean30     public Brave brave(SpanCollector spanCollector) {31         Brave.Builder builder = new Brave.Builder("asyn4 - service4 - 4");//指定serviceName32         builder.spanCollector(spanCollector);33         builder.traceSampler(Sampler.create(1));//采集率34         return builder.build();35     }36 37     @Bean38     public BraveServletFilter braveServletFilter(Brave brave) {39         /**40          * 设置sr、ss拦截器41          */42         return new BraveServletFilter(brave.serverRequestInterceptor(), 43                                       brave.serverResponseInterceptor(),44                                       new DefaultSpanNameProvider());45     }46 47 }
View Code

说明:指定了serviceName:"asyn4 - service4 - 4"

4.3、ZipkinAsyncController

技术分享
 1 package com.xxx.service4.zipkin.brave.async; 2  3 import org.springframework.web.bind.annotation.RequestMapping; 4 import org.springframework.web.bind.annotation.RequestMethod; 5 import org.springframework.web.bind.annotation.RestController; 6  7 import io.swagger.annotations.Api; 8 import io.swagger.annotations.ApiOperation; 9 10 @Api("zipkin brave async api")11 @RestController12 @RequestMapping("/zipkin/async/service4")13 public class ZipkinAsyncController {14 15     @ApiOperation("trace第4步")16     @RequestMapping(value = "http://www.mamicode.com/test4", method = RequestMethod.GET)17     public String myboot3() {18 19         try {20             return "async - service4";21         } catch (Exception e) {22             e.printStackTrace();23             return "";24         }25     }26 27 }
View Code

 

二、测试结果

1、依赖关系图:

技术分享

 

2、span时间消耗图

技术分享

 

3、详情图

点击第4个span,查看详情:

技术分享

第二十八章 springboot + zipkin(brave定制-AsyncHttpClient)