Android Retrofit源码解析

1.Retrofit是什么

retrofit是什么,Retrofitsquare公司全家桶中的一员,基于OkHttp二次封装的网络请求框架,使用了大量注解进行封装。

2.Retrofit优点,为什么使用它

上面说到retrofit是基于OkHttp封装的,那么为什么要使用它呢,它有以下优点:

  • 基于OkHttp,继承了OkHttp的优点,拥有socket连接池
  • 使用了注解,使得接口的定义跟接口的使用解耦
  • 提供了convert转换器,可以快速进行各种数据转换
  • 可以集成rxjava,使得异步请求不必要考虑更多操作

通过上面这么多优点介绍,我们还有不使用它的理由吗?

话不多说,先上示例代码,通过示例代码带大家了解retrofit。

3.示例代码

这是网络接口定义


import okhttp3.ResponseBody
import retrofit2.Call
import retrofit2.http.GET
import retrofit2.http.Query
import retrofit2.http.Streaming
import retrofit2.http.Url

interface NetApi {

    @GET("getLasterExcelInfo")
    fun getLastExcelInfo(@Query("fromType") fromType: Int, @Query("projectType") projectType: Int): Call<BaseResult>

    @Streaming
    @GET
    fun downloadExcel(@Url url: String): Call<ResponseBody>

}
 //1.创建retrofit对象
    var retrofit: Retrofit = Retrofit.Builder()
        .baseUrl("http://...")
        .addConverterFactory(GsonConverterFactory.create())
        .build()
    var netApi = retrofit.create(NetApi::class.java)

    var call = netApi.getLastExcelInfo(1, 1)
    call.enqueue(object : Callback<BaseResult> {

        override fun onFailure(call: Call<BaseResult>?, t: Throwable?) {
            println("失败")
        }

        override fun onResponse(call: Call<BaseResult>?, response: Response<BaseResult>?) {
            var response = response?.body()
            println("成功" + response.toString())
        }

    })

    netApi.downloadExcel("http://...")
        .enqueue(object : Callback<ResponseBody> {
            override fun onFailure(call: Call<ResponseBody>?, t: Throwable?) {
                println("下载文件失败")
            }

            override fun onResponse(call: Call<ResponseBody>?, response: Response<ResponseBody>?) {
                println("下载文件成功")
                var inputStream = response?.body()?.byteStream()
                var file = File("F://libraryquestions_1_1_1.xls")
                var os = FileOutputStream(file)
                var ch: Int?

                while (((inputStream?.read()).also { ch = it }) != -1){
                    if (ch != null)
                        os.write(ch!!)
                }
                os.flush()
                os.close()
            }

        })

 

上面是retrofit的简单使用,一个是get请求,一个为下载文件。是用kotlin写的,如果大家不熟悉kotlin可以略过不看,不影响我们对retrofit的源码简单分析。

那么通过上面可以总结出retrofit使用三步走:

  1. .构建retrofit对象,主要是运用构造者模式,设置baseurl、数据解析器、设置okhttpclient等。
  2. 通过动态代理模式获取功能接口对象
  3. 通过功能接口对象invoke方法返回Call对象执行enqueue、execute方法

4.源码分析

开始我们的主题,通过上面大家对retrofit有了基本认识,下面我们通过retrofit三步走来分析源码。

首先我们分析第一步生成retrofit

我给大家转成java代码

Retrofit retrofit = new Retrofit.Builder() .baseUrl("") .addConverterFactory(GsonConverterFactory.create()) .build();

通过如上图所示,内部是实现了构建者模式,进行各种设置baseurl、转换器、okhttpclient(没有设置的话会新建一个)等,这部分代码大家可以自己点击进去查看,很简单。

下面给大家分析第二步,很重要,动态代理生成接口类

大家注意我勾选的俩部分,其中

 Proxy.newProxyInstance(service.getClassLoader()运用了动态代理技术返回不同的接口service实例,大家不明白动态代理的可以参考我下一篇文章。

下面这一步很重要

ServiceMethod serviceMethod = loadServiceMethod(method);

大家注意这句代码,我们进去是下面这段代码

 ServiceMethod loadServiceMethod(Method method) {
    ServiceMethod result;
    synchronized (serviceMethodCache) {
      result = serviceMethodCache.get(method);
      if (result == null) {
        result = new ServiceMethod.Builder(this, method).build();
        serviceMethodCache.put(method, result);
      }
    }
    return result;
  }

我进入result = new ServiceMethod.Builder(this, method).build();这个build中

上面我们进入了这个方法里面,大家是不是很熟悉,这正是我们的接口service上面的注解,

所以通过上面的分析,大致就是通过动态代理,反射拿到类class对象,然后通过获取类的注解上面的值,进行各种判断,获取参数等生成request对象。

 private okhttp3.Call createRawCall() throws IOException {
    Request request = serviceMethod.toRequest(args);
    okhttp3.Call call = serviceMethod.callFactory.newCall(request);
    if (call == null) {
      throw new NullPointerException("Call.Factory returned null.");
    }
    return call;
  }

//生成reqesut跟call对象,在OkHttpCall实体中

然后第三步,将运用service接口对象调用方法返回call对象调用enqueue跟execute方法

 

上面只是个人通过查看retrofit源码了解到的,大家不喜勿喷,欢迎留言评论,指出不足之处!!!

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 1
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值