网络通信系列文章序
彻底掌握网络通信(一)Http协议基础知识
彻底掌握网络通信(二)Apache的HttpClient基础知识
彻底掌握网络通信(三)Android源码中HttpClient的在不同版本的使用
彻底掌握网络通信(四)Android源码中HttpClient的发送框架解析
彻底掌握网络通信(五)DefaultRequestDirector解析
彻底掌握网络通信(六)HttpRequestRetryHandler解析
彻底掌握网络通信(七)ConnectionReuseStrategy,ConnectionKeepAliveStrategy解析
彻底掌握网络通信(八)AsyncHttpClient源码解读
彻底掌握网络通信(九)AsyncHttpClient为什么无法用Fiddler来抓包
彻底掌握网络通信(十)AsyncHttpClient如何发送JSON解析JSON,以及一些其他用法
前面简单说了下DefaultRequestDirector的具体请求过程,这篇主要分析下HttpRequestRetryHandler类
1:该类的作用
1)请求计数,当发生异常的时候,如果重试次数大于某个值,则重连结束
2)当且仅当是可恢复的异常,才能进行重连
2:该类的具体实现
我们通过DefaultHttpClient可以知道,HttpRequestRetryHandler的实现者为DefaultHttpRequestRetryHandler
3:该类的默认构造函数
public DefaultHttpRequestRetryHandler() {
this(3, false);
}
public DefaultHttpRequestRetryHandler(int retryCount, boolean requestSentRetryEnabled) {
super();
this.retryCount = retryCount;
this.requestSentRetryEnabled = requestSentRetryEnabled;
}
我们知道,在DefaultRequestDirector的execute方法中,是通过while (retrying) {}的方式来不断的循环发送的,当且仅当一次连接正常响应后,retrying会被重置为false,退出循环;如果在一次请求过程中,发生异常,我们就会使用到HttpRequestRetryHandler来判断如何进行重连,我们看下判断是否重连的逻辑
/**
* Used <code>retryCount</code> and <code>requestSentRetryEnabled</code> to determine
* if the given method should be retried.
*/
public boolean retryRequest(
final IOException exception,
int executionCount,
final HttpContext context) {
if (exception == null) {
throw new IllegalArgumentException("Exception parameter may not be null");
}
if (context == null) {
throw new IllegalArgumentException("HTTP context may not be null");
}
//如果重试次数大于retryCount,默认为3此,则返回false,则execute方法会抛出对应异常
if (executionCount > this.retryCount) {
// Do not retry if over max retry count
return false;
}
//NoHttpResponseException也是一种可以重试的异常,return true则打印下异常日志
if (exception instanceof NoHttpResponseException) {
// Retry if the server dropped connection on us
return true;
}
//InterruptedIOException也是一种不可以重试的异常,return false则抛出异常
if (exception instanceof InterruptedIOException) {
// Timeout
return false;
}
//UnknownHostException也是一种不可以重试的异常,return false则抛出异常
if (exception instanceof UnknownHostException) {
// Unknown host
return false;
}
//SSLHandshakeException也是一种不可以重试的异常,return false则抛出异常
if (exception instanceof SSLHandshakeException) {
// SSL handshake exception
return false;
}
Boolean b = (Boolean)
context.getAttribute(ExecutionContext.HTTP_REQ_SENT);
boolean sent = (b != null && b.booleanValue());
if (!sent || this.requestSentRetryEnabled) {
// Retry if the request has not been sent fully or
// if it's OK to retry methods that have been sent
return true;
}
// otherwise do not retry
return false;
}
顾并不是所有的异常我们都建议或者可以重试的,可以重连的异常有NoHttpResponseException,ConnectTimeoutException ,SocketTimeoutException等