设为首页 加入收藏

TOP

Okhttp3源码解析(5)-拦截器RetryAndFollowUpInterceptor(二)
2019-09-03 03:44:36 】 浏览:109
Tags:Okhttp3 源码 解析 拦截 RetryAndFollowUpInterceptor
eamed HTTP body", response.code()); } if (!sameConnection(response, followUp.url())) { streamAllocation.release(); streamAllocation = new StreamAllocation(client.connectionPool(), createAddress(followUp.url()), call, eventListener, callStackTrace); this.streamAllocation = streamAllocation; } else if (streamAllocation.codec() != null) { throw new IllegalStateException("Closing the body of " + response + " didn't close its backing stream. Bad interceptor?"); } request = followUp; priorResponse = response; } } ``` 我先贴出一个`while循环`的流程图: ![](https://img2018.cnblogs.com/blog/1312938/201908/1312938-20190829084745296-805720763.png) 根据流程图和源码可以分析`RetryAndFollowUpInterceptor`主要做了以下内容,**后两点都是发生在`while循环`中**: - **初始化StreamAllocation 对象** - **网络请求-chain.proceed() ,对在请求时发生的异常进行捕获以及对应的重连机制** - **followUpRequest 对响应码进行处理** 下面可以逐块代码分析: ###### 1.初始化StreamAllocation 对象 `StreamAllocation`类是**协调三个实体之间的关系** 三个实体是:`Connections`,`Streams`,`Calls` 我们请求网络时需要传递它 ![](https://img2018.cnblogs.com/blog/1312938/201908/1312938-20190829084745679-501952792.png) `StreamAllocation`在这大家简单了解一下就可以了. ###### 2.网络请求时异常捕获-以及重连机制 网络请求如下: ``` response = realChain.proceed(request, streamAllocation, null, null); ``` 如果请求发现异常,我们通过try/catch捕获 ``` catch (RouteException e) { // The attempt to connect via a route failed. The request will not have been sent. if (!recover(e.getLastConnectException(), streamAllocation, false, request)) { throw e.getFirstConnectException(); } releaseConnection = false; continue; } catch (IOException e) { // An attempt to communicate with a server failed. The request may have been sent. boolean requestSendStarted = !(e instanceof ConnectionShutdownException); if (!recover(e, streamAllocation, requestSendStarted, request)) throw e; releaseConnection = false; continue; } ``` -`RouteException` 路由异常 - `IOException` IO异常 捕获后都做了`recover()`重连判断,具体代码如下,就不细说了: ``` private boolean recover(IOException e, StreamAllocation streamAllocation, boolean requestSendStarted, Request userRequest) { streamAllocation.streamFailed(e); // The application layer has forbidden retries. if (!client.retryOnConnectionFailure()) return false; // We can't send the request body again. if (requestSendStarted && userRequest.body() instanceof UnrepeatableRequestBody) return false; // This exception is fatal. if (!isRecoverable(e, requestSendStarted)) return false; // No more routes to attempt. if (!streamAllocation.hasMoreRoutes()) return false; // For failure recovery, use the same route selector with a new connection. return true; } ``` 这里需要注意的是如果可以重连,执行 continue; `continue`含义: 继续循环,(不执行 循环体内`continue` 后面的语句,直接进行下一循环) ###### 3.` followUpRequest` 对响应码进行处理 先看看具体`followUpRequest `方法: ``` private Request followUpRequest(Response userResponse, Route route) throws IOException { if (userResponse == null) throw new IllegalStateException(); int responseCode = userResponse.code(); final String method = userResponse.request().method(); switch (responseCode) { case HTTP_PROXY_AUTH: Proxy selectedProxy = route != null ? route.proxy() : client.proxy(); if (selectedProxy.type() != Proxy.Type.HTTP) { throw new ProtocolException("Received HTTP_PROXY_AUTH (407) code while not using proxy"); } return client.proxyAuthenticator().authenticate(route, userResponse); case HTTP_UNAUTHORIZED: return cli
首页 上一页 1 2 3 4 下一页 尾页 2/4/4
】【打印繁体】【投稿】【收藏】 【推荐】【举报】【评论】 【关闭】 【返回顶部
上一篇亲,麻烦给个五星好评!—RatingB.. 下一篇Android开发笔记

最新文章

热门文章

Hot 文章

Python

C 语言

C++基础

大数据基础

linux编程基础

C/C++面试题目