Retrofit2源码初探

Retrofit2源码初探

  Retrofit是Square面向安卓平台提供的http客户端开源网络库,官网上用一句话介绍:

A type-safe HTTP client for Android and Java

  本文就Retrofit2源码进行探讨,粗略分析其运行原理。分析代码版本为2.0.3-SNAPSHOT,官网:Retrofit主页github地址

Retrofit2框架一览

  Retrofit2相比于Retrofit1.X的调用有些许不同,而且提供直接取消正在进行任务的接口。其调用如下:

  interface PageService {
    @GET Call<Page> get(@Url HttpUrl url);
  }

  public static void main(String... args) throws Exception {
    OkHttpClient okHttpClient = new OkHttpClient.Builder()
        .connectionPool(new ConnectionPool(100, 30, TimeUnit.SECONDS))
        .build();

    Retrofit retrofit = new Retrofit.Builder()
        .baseUrl(HttpUrl.parse("https://example.com/"))
        .addConverterFactory(mConverterFactory)
        .client(okHttpClient)
        .build();

    PageService pageService = retrofit.create(PageService.class);
    //同步
    pageService.get(HttpUrl.parse(args[0])).execute();
    //异步
    pageService.get(HttpUrl.parse(args[0])).enqueue(new Callback<Page>() {
        ....
    });
  }

  Retrofit2依赖于Square自家的网络库OkHttp,OkHttp相当于网络请求中的传输层,Retrofit2在其上提供Http服务。retrofit2.Retrofit类是框架主要操作类,利用其设置参数,生成调用接口。在Retrofit2框架中需要关注以下几个类:

  • Retrofit:框架主要操作类,提供网络参数设置接口
  • ServiceMethod:将接口方法转换为http请求,框架的核心类
  • OkHttpCall:实现Call接口,封装okhttp操作
  • Converter.Factory:Converter转换器工厂
  • CallAdpter:将Call转换为T的适配器

      Retrofit2代码相对简洁,缺乏繁琐的抽象接口定义,可读性稍差。以上几个类组成并实现了Retrofit2框架的主要功能。

retrofit2.Retrofit

  Retrofit是框架主要操作类,使用Retrofit.Builder创建,Builder可以设置baseUrl,CallAdapterFactory,ConverterFactory,callbackExecutor等参数。Retrofit提供callFactory,requestBodyConverter,responseBodyConverter,callAdapter等方法获得运行时设置。

  Builder初始化使用Platform.get获得当前平台信息,Platform是对运行平台的抽象,在Android平台,callback默认回调到主线程。

    //Retrofit.Builder构造函数
    public Builder() {
      this(Platform.get());
    }

    Builder(Platform platform) {
      this.platform = platform;
      //设置默认converterFactory为BuiltInConverters
      converterFactories.add(new BuiltInConverters());  
    }

  Retrofit的create方法利用动态代理生成调用接口实例。create实现如下:

  public <T> T create(final Class<T> service) {
    ....  //忽略代码
    return (T) Proxy.newProxyInstance(service.getClassLoader(), new Class<?>[] { service },
        new InvocationHandler() {
          private final Platform platform = Platform.get();

          @Override public Object invoke(Object proxy, Method method, Object... args) throws Throwable {
            //忽略Object自身方法
            if (method.getDeclaringClass() == Object.class) {
              return method.invoke(this, args);
            }
            if (platform.isDefaultMethod(method)) {
              return platform.invokeDefaultMethod(method, service, proxy, args);
            }
            //利用ServiceMethod将接口方法转换为ServiceMethod
            ServiceMethod serviceMethod = loadServiceMethod(method);
            //生成OkHttpCall对象,OkHttpCall是Call接口的实现类,封装okhttp库操作
            OkHttpCall okHttpCall = new OkHttpCall<>(serviceMethod, args);
            //利用CallAdapter<T>将Call转换为T类型
            return serviceMethod.callAdapter.adapt(okHttpCall);
          }
        });
  }

  create方法是Retrofit2框架的主要实现环节,在安卓平台下,默认callAdpter将OkHttpCall转换为ExecutorCallbackCall,即把Callback回调接口放到主线程运行。create利用ServiceMethod类对接口方法进行解析,并使用OkHttpCall封装Http请求过程,最后利用callAdpter完成线程转换或类型转换操作。

ServiceMethod

  Retrofit2利用ServiceMethod将接口方法信息转换为http请求。ServiceMethod通过Builder创建,创建时对接口方法注解、方法参数注解进行解析。ServiceMethod提供toRequest,toResponse生成OkHttp的Request和Response。ServiceMethod对象创建过程如下:

method解析

  ServiceMethod对象创建时对接口方法进行解析,在解析方法参数注解时生成ParameterHandler列表,ParameterHandler的不同类型对应不同的参数注解,子类重写apply方法,实现不同注解下http请求创建操作。

  ServiceMethod的toRequest方法利用RequestBuilder创建Request类,RequestBuilder封装了创建过程的一系列操作。OkHttpCall对象初始化需要传入ServiceMethod引用,OkHttpCall对象在其内部调用ServiceMethod的toRequest方法生成Request,从而调用OkHttp库实现网络请求。

Converter.Factory

  Converter代表内容转换类,Converter.Factory是其工厂类,Retrofit通过Converter.Factory类提供转换器。Converter.Factory定义如下:

  abstract class Factory {
    // Responsebody转换
    public Converter<ResponseBody, ?> responseBodyConverter(Type type, Annotation[] annotations, Retrofit retrofit) {
      return null;
    }

    // Requestbody转换
    public Converter<?, RequestBody> requestBodyConverter(Type type,
        Annotation[] parameterAnnotations, Annotation[] methodAnnotations, Retrofit retrofit) {
      return null;
    }

    // 字符串转换,用@Field,@FieldMap,@Path等注解值转换
    public Converter<?, String> stringConverter(Type type, Annotation[] annotations, Retrofit retrofit) {
      return null;
    }
  }

  Retrofit类包含Converter.Factory列表,通过遍历获取合适的转换器工厂生成合适的转换器。Retrofit支持gson,jackson,moshi,protobuf,simplexml,wire等解析库,为了减少对其他类库的依赖,Retrofit把对解析库的支持放到子项目中,例如项目需要支持gson加上:

compile("com.squareup.retrofit2:retrofit-converters:2.0.3-SNAPSHOT")

  Retrofit默认提供BuiltInConverters生成转换器,默认的转换器对内容基本不作修改返回。

CallAdpter

  Retrofit通过CallAdpter支持guava,java8,rxjava的事件驱动模型。同样,为了减少依赖,Retrofit把这部分代码放在独立子项目中,使用时添加类库依赖即可。

  在Android平台下,默认CallAdapterFactory为ExecutorCallAdapterFactory,重写get方法返回匿名adpter,将传入的Call转换为ExecutorCallbackCall,即把callback回调到主线程。

总结

  Retrofit2封装Okhttp网络库,提供http客户端服务,框架支持丰富的方法注解和参数注解,使用方便。同时支持gson,jackson,rxjava等第三方开源库。

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

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

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值