retrofit 源码分析

callAdater可以设置RxJava2CallAdapter,目前只可用这个adapter,支持rxjava2的操作;convertAdater可以使用多种进行操作。

调用例子:

Retrofit retrofit = builder.baseUrl("https://api.github.com")
        .client(client)
        .build();
return retrofit.create(serviceClass);

通过创建Retrofit分析得到,数据的内容为public <T> T create(final Class<T> service) {};传入的参数是一个类型Class的类型,返回的也是这个class实例对象,这里返回的

是serviceClass类对象。这个对象未进行初始化操作,就是里面的接口的函数实例未进行初始化。会使用动态代理创建一个newProxyInstance对象,通过传入的InvocationHandler类进行操作。

retrofit 创建类变量,创建时需要下面的变量进行初始化,callFactory通过client的方法进行设置;baseurl就是链接的网址;converterFactories转换发送和接收的json报文信息,或者组包
请求的数据包。adapterFactories执行rxjava的RxJava2CallAdapterFactory、callbackExecutor平台创建的执行回掉,普通的java平台和安卓平台;

 reponse 返回的convert匹配方法,通过判断

通过日志可以监控到,retrofit默认的有一个BuiltInConverters

 

public abstract io.reactivex.Single com.seuic.getuser.EventService.getFollowing(long)传入的method是一个抽象的方法,返回的结果是servicemethod的对象,在创建servicemethod的时候,会初始化所有参数,各种adapter,具体的详细field如下图所示:

  ServiceMethod(Builder<R, T> builder) {
    this.callFactory = builder.retrofit.callFactory();
    this.callAdapter = builder.callAdapter;
    this.baseUrl = builder.retrofit.baseUrl();
    this.responseConverter = builder.responseConverter;
    this.httpMethod = builder.httpMethod;
    this.relativeUrl = builder.relativeUrl;
    this.headers = builder.headers;
    this.contentType = builder.contentType;
    this.hasBody = builder.hasBody;
    this.isFormEncoded = builder.isFormEncoded;
    this.isMultipart = builder.isMultipart;
    this.parameterHandlers = builder.parameterHandlers;
  }

servicemethod类提供了创建okhttp的请求组包,在okhttpcall中被调用,toRequest函数返回一个请求的 对象;

CallExecuteObservable》OkHttpCall》servicemethod里的okhttp的client和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;
  }

okhttp的call是在rxjava2 calladpter运行的。执行的结果如下图所示

 

 retrofit http请求返回类型说明,返回类型通过类型解析获取到,最终返回的类型为Page<user>的类

public interface EventService {
    @GET("users/{username}/received_events")
    Single<Response<Page<User>>> getUserRecievedEvents(@Path("username") String username, @Query("page") long page);

    @GET("/user/following")
    Single<Response<Page<User>>> getFollowing(@Query("page") long page);
}

关于convertadpater匹配说明,实际的使用中,可以设置多个convertadpater,但是最终的选择是根据返回的类型进行解析选定的,就是

        int start = converterFactories.indexOf(skipPast) + 1;
        for (int i = start, count = converterFactories.size(); i < count; i++) {
            Converter<ResponseBody, ?> converter = converterFactories.get(i).responseBodyConverter(type, annotations, this);
            if (converter != null) {
                //noinspection unchecked
                return (Converter<ResponseBody, T>) converter;
            }
        }

type:当前请求返回的类型,本例中就是page,通过代码跟踪可以看到,循环的匹配查找当前的adpater里类型与type是否一致,不一致就返回null,继续寻找下一个,直接遇到moshi这个对象,直接把type传入进去,创建一个转换的adatper,可以将json转换成指定的class 对象,所以这里可以添加多个convertadatper,可以在需要用的时候直接调用;如果不添加,会默认一个convert,用户可以写自己的convert,然后添加进去。

当且仅当调用everntservice里面的函数的时候,才会运行调用InvocationHandler里面的invoke函数,在创建retrofit接口实例的时候不会调用invoke回掉

1、retrofit模块对象说明,主要提供设置请求地址设置,创建callAdapter和convertAdpter对象的实例化。以及create实现的动态代理调用,create是调用的核心代码,实现一个接口的实例。

 

2、ServiceMethod对象提供请求和解析的功能,给okhttp的回掉使用;生成http请求的body,同时解析返回的body数据;在build的时候解析http数据包的各个字段,例如
head和body等信息,创建http请求时需要该字段。

 

 OkHttpCall类继承了call接口,该对象主要是okhttp请求操作,对call接口的实现,该接口提供给rxjavaAdapter使用

 

posted on 2017-10-26 15:41  tistar  阅读(151)  评论(0编辑  收藏  举报