Retrofit源碼解讀(三)--RxJavaCallAdapterFactory講解

Retrofit源碼解讀(三)--RxJavaCallAdapterFactory講解

標(biāo)簽(空格分隔):Retrofit源碼


前言

  • 以下的相關(guān)知識總結(jié)是通過慕課網(wǎng)的相關(guān)學(xué)習(xí)和自己的相關(guān)看法,如果有需要的可以去查看一下慕課網(wǎng)的相關(guān)教學(xué),感覺還可以。

父類

which uses RxJava for creating observables

 final class RxJavaCallAdapterFactory extends CallAdapter.Factory

我們可以看到這個RxJavaCallAdapterFactory繼承的是Factory這個類,我們可以點進入可以看到Factory是CallAdapter這個接口的一個抽象類

Calladapter流程

就是把Retrofit里面的Call這個泛型對象轉(zhuǎn)換成我們的java對象,通過這個java對象來進行數(shù)據(jù)轉(zhuǎn)換,UI顯示等等。。

Call<T> ---> Java對象

這里的Retrofit里面的Call<T>不同于okhttp里面的Call<T>,這里的是對于OkHttp的一個封裝,也就是說我們通過Retrofit來進行網(wǎng)絡(luò)請求,其實質(zhì)就是通過OkHttp來進行的網(wǎng)絡(luò)請求,只不過Retrofit封裝了一層。

如何轉(zhuǎn)換成java對象

創(chuàng)建Call<T>對象,通過調(diào)用OkHttp請求,拿到服務(wù)器返回給我們的數(shù)據(jù),這個時候通過我們的converter這個數(shù)據(jù)轉(zhuǎn)換器,把服務(wù)器給我們返回回來的response轉(zhuǎn)換為我們需要的java對象,其中這個converter可以在我們創(chuàng)建retrofit實例的時候進行個性化的配置,比如addConverterFactory(GsonConverterFactory.create()) //設(shè)置數(shù)據(jù)解析器  默認使用的Gson

源碼分析


CallAdapter的成員變量
  • Type responseType();這個方法就是返回http請求返回后的類型,這個就是我們接口中的泛型的實參,比如如下:

Returns the value type that this adapter uses when converting the HTTP response body to a Java

  • object. For example, the response type for {@code Call<Repo>} is {@code Repo}. This type
  • is used to prepare the {@code call} passed to {@code #adapt}.
 @GET("article/list/latest?page=1")
    Call<HttpResult<List<TestBean>>> getQiuShiJsonString();
那么這個Type就是HttpResult<List<TestBean>>這個實例
  • T adapt(Call<R> call);
    這個就是返回的是Retrofit里面的Call對象,如果是RxJava的話,那么返回的就是一個 Observable<?> 也就是類似下面我們使用RxJava的接口類型
 Observable<BaseModel<ArrayList<PersonInfoBean.PersonalFood>>>

Factory內(nèi)部抽象類

   這個就是根據(jù)我們的接口返回類型,注解類型得到我們實際需要的CallAdapter
   /**
     * Returns a call adapter for interface methods that return {@code returnType}, or null if it
     * cannot be handled by this factory.
     */
    public abstract @Nullable CallAdapter<?, ?> get(Type returnType, Annotation[] annotations,
        Retrofit retrofit);
  /**
     * Extract the upper bound of the generic parameter at {@code index} from {@code type}. For
     * example, index 1 of {@code Map<String, ? extends Runnable>} returns {@code Runnable}.
     */
    protected static Type getParameterUpperBound(int index, ParameterizedType type) {
      return Utils.getParameterUpperBound(index, type);
    }
獲取我們的原始的類型
 /**
     * Extract the raw class type from {@code type}. For example, the type representing
     * {@code List<? extends Runnable>} returns {@code List.class}.
     */
    protected static Class<?> getRawType(Type type) {
      return Utils.getRawType(type);
    }

RxJavaCallAdapterFactory代碼

1、繼承Factory

public final class RxJavaCallAdapterFactory extends CallAdapter.Factory {

2、注冊CallAdapter

addCallAdapterFactory(RxJavaCallAdapterFactory.create())

3、調(diào)用Factory.get方法來獲取我們的CallAdapter

 @Override
  public CallAdapter<?, ?> get(Type returnType, Annotation[] annotations, Retrofit retrofit) {
    //獲取到原始數(shù)據(jù)類型
    Class<?> rawType = getRawType(returnType);
    以下代碼省略
    / 。。。/
   
    //最終返回一個RxJavaCallAdapter  進行類型轉(zhuǎn)換
    return new RxJavaCallAdapter(responseType, scheduler, isAsync, isResult, isBody, isSingle,
        false);
  }
 

4、調(diào)用adapt方法來講Call請求轉(zhuǎn)換

  @Override public Object adapt(Call<R> call) {
  
  //這個時候把retrofit的Call這個對象傳進來,這個然后通過
    OnSubscribe<Response<R>> callFunc = isAsync
        ? new CallEnqueueOnSubscribe<>(call)
        : new CallExecuteOnSubscribe<>(call);

    OnSubscribe<?> func;
    if (isResult) {
      func = new ResultOnSubscribe<>(callFunc);
    } else if (isBody) {
      func = new BodyOnSubscribe<>(callFunc);
    } else {
      func = callFunc;
    }
    // 通過Observable<?> observable 和Call創(chuàng)建關(guān)聯(lián) 可以看到func的創(chuàng)建和Call是有關(guān)聯(lián)的
    Observable<?> observable = Observable.create(func);
    //判斷調(diào)度器是否為空
    if (scheduler != null) {
      observable = observable.subscribeOn(scheduler);
    }
    
    if (isSingle) {
      return observable.toSingle();
    }
    if (isCompletable) {
      return CompletableHelper.toCompletable(observable);
    }
    //直接返回observable
    return observable;
  }

總結(jié)

  • 理論:
    獲取到一個Call<T>對象,拿到這個Call<T>對象去執(zhí)行http請求,而Retrofit調(diào)用這個Call請求,最終調(diào)用的還是okhttp里面的Call請求,只不過對其進行了封裝,通過這樣我們就可以獲取到服務(wù)器端返回的數(shù)據(jù),獲取到數(shù)據(jù)之后我們就會調(diào)用converter數(shù)據(jù)轉(zhuǎn)換器來把我們需要的對象轉(zhuǎn)換出來.

  • 實現(xiàn):

    • 實現(xiàn)Factory這個抽象類
    • 注冊CallAdapter到retrofit中
    • 通過Factory.get方法獲取到具體的CallAdapter
    • 在調(diào)用adapt這個方法,最終轉(zhuǎn)換成每一個平臺適用的類型
?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請聯(lián)系作者
【社區(qū)內(nèi)容提示】社區(qū)部分內(nèi)容疑似由AI輔助生成,瀏覽時請結(jié)合常識與多方信息審慎甄別。
平臺聲明:文章內(nèi)容(如有圖片或視頻亦包括在內(nèi))由作者上傳并發(fā)布,文章內(nèi)容僅代表作者本人觀點,簡書系信息發(fā)布平臺,僅提供信息存儲服務(wù)。

相關(guān)閱讀更多精彩內(nèi)容

友情鏈接更多精彩內(nèi)容