拦截器的执行顺序是是什么?


okhttp3.RealCall#getResponseWithInterceptorChainResponse getResponseWithInterceptorChain() throws IOException {// Build a full stack of interceptors.List<Interceptor> interceptors = new ArrayList<>();interceptors.addAll(client.interceptors());interceptors.add(new RetryAndFollowUpInterceptor(client));interceptors.add(new BridgeInterceptor(client.cookieJar()));interceptors.add(new CacheInterceptor(client.internalCache()));interceptors.add(new ConnectInterceptor(client));if (!forWebSocket) {interceptors.addAll(client.networkInterceptors());}interceptors.add(new CallServerInterceptor(forWebSocket));Interceptor.Chain chain = new RealInterceptorChain(interceptors, transmitter, null, 0,originalRequest, this, client.connectTimeoutMillis(),client.readTimeoutMillis(), client.writeTimeoutMillis());boolean calledNoMoreExchanges = false;try {Response response = chain.proceed(originalRequest);if (transmitter.isCanceled()) {closeQuietly(response);throw new IOException("Canceled");}return response;} catch (IOException e) {calledNoMoreExchanges = true;throw transmitter.noMoreExchanges(e);} finally {if (!calledNoMoreExchanges) {transmitter.noMoreExchanges(null);}}}

这里有定义顺序,我们也可以从调用堆栈里面看到整个拦截器执行的顺序。

调用堆栈

"OkHttp https://www.baidu.com/...@9689" prio=5 tid=0xae nid=NA runnablejava.lang.Thread.State: RUNNABLEat okhttp3.internal.http.CallServerInterceptor.intercept(CallServerInterceptor.java:37)at okhttp3.internal.http.RealInterceptorChain.proceed(RealInterceptorChain.java:142)at okhttp3.internal.connection.ConnectInterceptor.intercept(ConnectInterceptor.java:43)at okhttp3.internal.http.RealInterceptorChain.proceed(RealInterceptorChain.java:142)at okhttp3.internal.http.RealInterceptorChain.proceed(RealInterceptorChain.java:117)at okhttp3.internal.cache.CacheInterceptor.intercept(CacheInterceptor.java:94)at okhttp3.internal.http.RealInterceptorChain.proceed(RealInterceptorChain.java:142)at okhttp3.internal.http.RealInterceptorChain.proceed(RealInterceptorChain.java:117)at okhttp3.internal.http.BridgeInterceptor.intercept(BridgeInterceptor.java:93)at okhttp3.internal.http.RealInterceptorChain.proceed(RealInterceptorChain.java:142)at okhttp3.internal.http.RetryAndFollowUpInterceptor.intercept(RetryAndFollowUpInterceptor.java:88)at okhttp3.internal.http.RealInterceptorChain.proceed(RealInterceptorChain.java:142)at okhttp3.internal.http.RealInterceptorChain.proceed(RealInterceptorChain.java:117)at com.example.okhttptest.MainActivity$1.intercept(MainActivity.java:27)at okhttp3.internal.http.RealInterceptorChain.proceed(RealInterceptorChain.java:142)at okhttp3.internal.http.RealInterceptorChain.proceed(RealInterceptorChain.java:117)at okhttp3.RealCall.getResponseWithInterceptorChain(RealCall.java:229)at okhttp3.RealCall$AsyncCall.execute(RealCall.java:172)at okhttp3.internal.NamedRunnable.run(NamedRunnable.java:32)at java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1167)at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:641)at java.lang.Thread.run(Thread.java:919)

如何拦截替换请求

        OkHttpClient okHttpClient = new OkHttpClient.Builder().addInterceptor(new Interceptor() {@Overridepublic Response intercept(Chain chain) throws IOException {Request request = chain.request().newBuilder().url("https://www.sina.com.cn/").build();return chain.proceed(request);}}).build();

如果手机没有网,那么重试拦截器会重试吗?

不会

各层拦截器的作用是什么?

在 RealCall 中会按照顺序添加如下几个默认的 Interceptor 到责任链中用来完成基本功能:

用户设置的 Interceptor
RetryAndFollowUpInterceptor:失败重试及重定向
BridgeInterceptor:处理网络 Header、Cookie、gzip 等
CacheInterceptor:管理缓存
ConnectInterceptor:连接服务器
如果是 WebSocket 请求则添加对应的 Interceptors
CallServerInterceptor:数据发送/接收

networkInterceptors 和 Interceptors 的区别是什么?

执行顺序不一样,如果遇到304 重定向,netWorkInteceptors 能够监听到,而普通的application interceptors监听不到。application interceptors 只调用一次,不会处理到304.

所有的拦截器没有使用for 循环,是怎么进行按照顺序调用的?

RealInterceptorChain 调用 第一个 Interceptors 的 process 方法,第一个Interceptors 的process 方法中会调用下一个拦截器的intercept 方法,

okhttp3.internal.http.RealInterceptorChain#proceed() 注定会创建一个新的RealInterceptorChain,然后调用下一个拦截器的intercept 方法,并传入下一个chain,interceptor 处理完就调用chain 的process,chain 的 process 会获取到下一个拦截器,并传递下一次chain,就可以层层传递。

异步任务线程的名字在哪里定义的?

OkHttp https://www.baidu.com/…

public abstract class NamedRunnable implements Runnable {protected final String name;public NamedRunnable(String format, Object... args) {this.name = Util.format(format, args);}@Override public final void run() {String oldName = Thread.currentThread().getName();Thread.currentThread().setName(name);try {execute();} finally {Thread.currentThread().setName(oldName);}}protected abstract void execute();
}

一些参考:

https://zhuanlan.zhihu.com/p/104813091

OkHttp 源码解析---拦截器相关推荐

  1. Android OkHttp 源码解析 - 拦截器

    一.前言 看一下 RealCall 中的拦截器排序: Response getResponseWithInterceptorChain() throws IOException {// Build a ...

  2. Spring AOP源码解析-拦截器链的执行过程

    一.简介 在前面的两篇文章中,分别介绍了 Spring AOP 是如何为目标 bean 筛选合适的通知器,以及如何创建代理对象的过程.现在得到了 bean 的代理对象,且通知也以合适的方式插在了目标方 ...

  3. 彻底理解OkHttp - OkHttp 源码解析及OkHttp的设计思想

    OkHttp 现在统治了Android的网络请求领域,最常用的框架是:Retrofit+okhttp.OkHttp的实现原理和设计思想是必须要了解的,读懂和理解流行的框架也是程序员进阶的必经之路,代码 ...

  4. OkHttp 源码解析(4.9.1 版本)

    文章目录 1.OkHttp 简介 2.OkHttp 配置与基本用法 2.1 依赖引入与配置 2.2 基本用法 3.OkHttp 常见对象介绍 4.OkHttp 源码解析 4.1 当我们调用`okhtt ...

  5. OkHttp源码解析(上)

    导语 学过Android开发的同学都知道,我们使用网络请求获取服务器的数据时,通常使用的是封装好的Retrofit框架,这个框架很好的帮助我们对网络的发起,以及返回的数据进行操作,我们使用起来十分方便 ...

  6. Spring AOP 源码分析 - 拦截器链的执行过程

    1.简介 本篇文章是 AOP 源码分析系列文章的最后一篇文章,在前面的两篇文章中,我分别介绍了 Spring AOP 是如何为目标 bean 筛选合适的通知器,以及如何创建代理对象的过程.现在我们的得 ...

  7. okhttp源码解析(五):代理和DNS

    前言 之前我们分析了okhttp的重试机制,发现在获取可用地址的时候,都需要遍历一个路由选择器,里面保存了可用的地址,那么这些地址是从哪来的呢?这就是本篇分析的重点. 首先我们简单理解一下代理和DNS ...

  8. 【cartographer源码解析--外推器】

    cartographer源码解析–外推器 文章目录 cartographer源码解析--外推器 前言 一.cartographer中的PoseExtrapolator类 二.接受数据,并分析处理逻辑 ...

  9. okHttp源码解析------待续

    看该篇文章前首先要熟悉okHttp的使用,建议先读OkHttp的简单使用 本文的源码解析参考链接:okhttp3总和解析 1.从URL请求处理开始分析 由异步将请求加入调度方法开始引入正题: getC ...

最新文章

  1. 如何在多线程中调用winform窗体控件2——实例篇
  2. Jenkins之gitlab配置
  3. [云炬创业学笔记]第一章创业是什么测试4
  4. 问题 E: 括号规则
  5. 在web前端调用后台java程序(java类)的方式
  6. 数据库连接池技术详解【吐血整理,疯狂推荐】
  7. php实现git服务器,如何搭建和配置Git服务器
  8. C#操作IIS完整解析
  9. DRBD安装配置、工作原理及故障恢复
  10. Roland SRX Series for Mac - 罗兰SRX系列音频插件合集
  11. 数据结构实训——哈希表设计
  12. 【数学建模】灰色模型
  13. 武汉大学计算机学院选考要求,武汉大学高考必选科目-考武汉大学需要选哪三科...
  14. 抖音电商广告后台分为哪些?它们其中又有什么区别?
  15. python语句中str_python中str是什么意思
  16. Centos7清理垃圾文件或过期文件
  17. 计算机网络软件组成,计算机网络软件的组成
  18. 如何让自己不再暴躁易怒
  19. JVM常用参数与工具
  20. htons() ntohl() ntohs() htons()的区别及详解

热门文章

  1. linux配置英文,linux 系统配置命令(国外英文资料).doc
  2. php数组转字符串 join,jQuery中将数组转换成字符串join()和push()使用
  3. get_sheet_of_light_result_object_model_3d算子说明
  4. linux中python如何调用matlab的数据_?如何在Python中加入多个数据帧?
  5. 《使用CSLA 2019:CSLA .NET概述》原版和机译文档下载
  6. RichTextBox读写数据库
  7. 用国内镜像源pip加速安装模块
  8. TaintDroid深入剖析之启动篇
  9. Spring常用工具类
  10. 报错-Unknown class in Interface Builder file