目标:
1).监控网络请求的各个阶段
2)获取每一个阶段的耗时和性能,用于性能分析。包括dns解析,socket连接时间,tls连接时间,请求发送时间,服务器接口处理时间,应答传输时间,应答数据处理时间等。
一、Okhttp全链路监控工具
Okhttp3提供了全链路监控工具EventListener。
1.1 注册全链路监听方法
OkhttpClient.Builder提供了注册链路监听的方法。
java
public Builder eventListener(EventListener eventListener) {
if (eventListener == null) {
throw new NullPointerException("eventListener == null");
} else {
this.eventListenerFactory = EventListener.factory(eventListener);
return this;
}
}
public Builder eventListenerFactory(EventListener.Factory eventListenerFactory) {
if (eventListenerFactory == null) {
throw new NullPointerException("eventListenerFactory == null");
} else {
this.eventListenerFactory = eventListenerFactory;
return this;
}
}
因此,用户只需要注册全链路监听方法,就可以在链路监听中进行逻辑处理。
1.2 全链路监控工具EventListener
一个HTTP请求过程主要如下:
1.callStart:一次请求开始了
2.dns:dns解析过程
3.connectStart: 开始建立连接了
4.secureConnect: 开始建立TSL安全链接
5.connectEnd: 链接建立结束:可能建立失败,失败后可以重试
6.requestHeaders:发送请求头
7.requestBody:发送请求body
8.服务器端处理请求
9.responseHeaders:客户端接受响应头
10.responseBody:客户端接受响应body
11.connectionReleased:链接释放
12.callEnd:一次请求结束
根据链路监听方法,我们对主要过程进行耗时计算:
请求时长=callEnd/callFailed - callStart=请求结束时间-请求开始时间
请求队列等待时间=dnsStart-callStart=DNS开始解析时间-请求开始时间
DNS解析时长=dnsEnd-dnsStart=DNS解析结束时间- DNS解析开始时间
TCP连接时长=secureConnectStart-connectStart=TLS连接开始时间-连接开始时间
TLS连接时长=secureConnectEnd-secureConnectStart=TLS连接结束时间- TLS连接开始时间
连接总时长=connectEnd/connectFailed-connectStart=连接结束时间/连接失败时间-连接开始时间
请求时长=requestBodyEnd-connectEnd=请求报文体结束时间-连接结束时间
服务器处理时长=responseHeadersStart-requestBodyEnd=响应头开始时间-请求体结束时间
应答响应时长=responseBodyEnd-responseHeadersStart=应答报文体结束时间-应答请求头开始时间
应答解析时间=callEnd-responseBodyEnd=请求结束时间-应答报文体结束时间
解析时间如果是Retrofit,可以在用户层进行二次解析。
另外还可以添加一些辅助监控信息
- 请求url:请求url。
- 请求方式 : get , post ....
- 是否Https:
- 是否开了代理:
- 上行流量:包括整个请求上行header和body的总的流量,包含重试和重定向的上行流量。用于监控上行流量开销。
- 下行流量:包括整个请求下行header和body的总的流量,包含重试和重定向的下行流量。用于监控下行流量开销。
- 目标IP地址:对于多出口IP的客户,支持IP地址维度的数据分析。
- dns解析结果:请求url的域名解析ip列表,用于分析是否存在域名劫持的问题。
- tls握手记录:用于排查问题
- http code:根据http code确定请求状态。
- 网络库类型及版本:对于客户更换网络库或者升级网络库版本的情况,可以提供前后的网络数据的差异。
- 网络状态:NO,2G,3G,4G,5G,WIFI
- 异常信息:异常信息主要是收集网络请求各阶段出现异常时的异常栈的信息。比如常见的java.net.UnknownHostException、java.net.SocketTimeoutException等。
二、增加全链路监听
2.1 构建监听对象
2.2 实现链路监听对象计算
2.3 监听结果回调
参考文献: