OkHttp源码分析(一)之同步/异步请求

版权声明:本文为博主原创文章,未经博主允许不得转载。 https://blog.csdn.net/qq_33706840/article/details/82944277

一、获取OkHttpClient实例


  1. 通过构造器模式获取实例,不太了解Builder模式的请移步
    构造器模式,主要关注Dispatcher分发器与ConnectionPool连接池。
    在这里插入图片描述
  2. 通过调用build()返回实例
    在这里插入图片描述

二、获取Request实例

  1. 同样是通过构造器模式获取实例,默认使用GET方法请求网络,同时可以看到Headers也使用构造器模式,源码如下:
    在这里插入图片描述

三、获取Call对象

  1. 通过client.newCall(request)获取RealCall对象,RealCall实现Call接口
    在这里插入图片描述
    2.接下来进入newRealCall方法内部,最终返回RealCall对象
    在这里插入图片描述
  2. RealCall构造方法中分别持有OkHttpClient实例与Request实例,同时初始化拦截器RetryAndFollowUpInterceptor
    在这里插入图片描述

四、异步请求网络

  1. 通过enqueue异步请求网络,实际是调用RealCall中的enqueue()方法
    在这里插入图片描述

  2. 首先内部使用synchronized关键字,首先判断executed是否为true,即是否是第一次执行,若为第一次执行则将executed置为true,也就是Call只能执行一次,然后注册监听器,每当调用enqueueexecute时会回掉其方法,最后通过Dispatcher来完成请求

  3. Dispatcher中的enqueue()是一个同步方法,首先判断运行的异步请求数是否小于最大请求数和运行的主机数是否小于最大主机数,若满足条件则将AsyncCall加入运行队列中,并通过线程池执行该异步请求,反之,加入到缓存队列中
    在这里插入图片描述

  4. executorService()创建线程池,可以看出最大线程池数量为Integer.MAX_VALUE,但是会受到maxRequests=64的影响,不太清楚线程池请移步 线程池
    在这里插入图片描述在这里插入图片描述

  5. AsyncCall继承NamedRunnableNamedRunnable实现了Runnable接口,在这里插入图片描述
    在这里插入图片描述

  6. AsyncCall实现NamedRunnable中的抽象方法execute(),判断拦截器是否取消通过Callback接口回调相应方法,可以看出回调结果在子线程中
    在这里插入图片描述

五、同步请求网络

  1. 首先会通过getResponseWithInterceptorChain初始化拦截器链,并获得response实例,同步则是通过runningSyncCalls.add(call);直接加入到请求队列中
    在这里插入图片描述

  2. finish()方法,同步代码块中首先从队列中移除call对象,若不能移除则抛出异常,同步中promoteCallsfalse,然后计算运行队列中的请求数量runningCallsCount()
    在这里插入图片描述

  3. runningCallsCount()中计算同步和异步运行就绪的请求队列中的请求数量即call对象数量
    在这里插入图片描述


猜你喜欢

转载自blog.csdn.net/qq_33706840/article/details/82944277
今日推荐