Retrofit面試該說些什麼

相信大家都用過Retrofit這個框架,但是面試官讓你說說retrofit這個框架往往面試者不知道怎麼回答,在這裏我給大家提供一個思路。

1、基本的使用。
第一步、通過Retrofit的builder模式創建一個retrofit對象,可以在builder裏面設置okhttpclient、baseurl、callAdapterFactroy、addConverterFactory等信息。
第二步、通過得到的retrofit對象加工要請求的接口,得到一個接口對象。
第三步、通過這個接口對象,調用接口裏面的方法得到一個網絡工作對象。
第四步、通過這個網絡工作對象調用enqueue方法或者execute方法發起請求並且回調回請求的結果。具體代碼如下:

     //1、通過builder方式創建一個retrofit對象,可以添加client baseurl addConverterFactory addCallAdapterFactory 等信息
        Retrofit retrofit = new Retrofit.Builder()
                .baseUrl("")
                .addConverterFactory(null)
                .addCallAdapterFactory(null)
                .client(null)
                .build();
        //2、通過retrofit.create加工得到一個網絡接口對象
        INetApiService iNetApiService = retrofit.create(INetApiService.class);
        //3、調用網絡接口對象的接口函數,得到一個網絡工作對象
        Call<Book> call = iNetApiService.getBook();
        //4、通過網絡工作對象發起一個請求並回調回請求的結果
        call.enqueue(new Callback<Book>() {
            @Override
            public void onResponse(Call<Book> call, Response<Book> response) {

            }
            @Override
            public void onFailure(Call<Book> call, Throwable t) {
            }
        });

從上面的用法就可以看到,retrofit的存在不是它去請求對象,它的作用是生成幫助開發者生成網絡請求對象的封裝,和按照接口返回對應的網絡工作對象,真正的網絡請求發生在網絡工作對象上的。

retrofit解決的問題:在以前做網絡請求的時候,會考慮到如何封裝請求數據,如何發起請求,到最後對返回數據的封裝分類都需要開發人員自己維護,開發成本大不說,還容易出錯。而retrofit通過簡單的配置就可以實現上面複雜的過程。所以要想拆分retrofit就要主要分爲三個方面來,請求數據的封裝,請求對象生成及其如何發起網絡請求的,最後對請求數據的封裝。任何網絡問題都逃不過這三部分。
1、請求數據(請求行、請求頭、請求體)的封裝。
2、生成請求對象發起請求。
3、響應數據的封裝(響應行、響應頭、響應體)。

2、retrofit的如何定製擴展。
擴展主要分爲三個方面
第一方面、用誰來生成網絡工作對象,在retrofit中雖然只能傳入一個OkhttpClient對象,但是okhttp有豐富的擴展性,可以定製自己的攔截器,可以實現數據的緩存等。
第二方面、生成的網絡工作對象進行轉換(我們實際進行請求的是okhttp3裏面的realCall,而在網絡接口中定義的Call對象是在retrofit2中定義的,所以需要一個適配器進行轉換),retrofit裏面添加rxJava支持,可以返回一個Observable對象。
第三方面、對網絡返回的數據進行解析,可以添加自己的數據解析器,定義自己的convertor類和ConvertorFactory類。

3、retrofit原理分析。

ServiceMethod 算是對請求數據的整體封裝
動態代理首先會爲每一方法生成一個ServiceMethod對象,存入緩存中,這個對象包含來網絡請求所用到的一切,請求方法、請求的連接、請求頭、callAdapter的適配器、convertor等信息。
如何找到合適的CallAdapter?
根據返回值找到對應的CallAdapter,如果是ExecuteCallAdapterFactory則返回的callAdapter對象爲CallAdapter,如果是Rxjava則返回的是Rxjava2CallAdapter對象

1、獲取當前方法的返回類型method.getGenericReturnType()。
2、遍歷添加的CallAdapterFactory數組,通過每一個factory的get方法裏面確認是否能創建該類型的對象,ExecutorCallAdapterFactory 代碼如下

  @Override
  public CallAdapter<?, ?> get(Type returnType, Annotation[] annotations, Retrofit retrofit) {
    if (getRawType(returnType) != Call.class) {
      return null;
    }
    final Type responseType = Utils.getCallResponseType(returnType);
    return new CallAdapter<Object, Call<?>>() {
      @Override public Type responseType() {
        return responseType;
      }
      @Override public Call<Object> adapt(Call<Object> call) {
        return new ExecutorCallbackCall<>(callbackExecutor, call);
      }
    };
  }

如何來確認responseConvertor對象呢?
通過泛型的返回值來進行選定的。Gson選定代碼如下

  @Override
  public Converter<ResponseBody, ?> responseBodyConverter(Type type, Annotation[] annotations,
      Retrofit retrofit) {
    TypeAdapter<?> adapter = gson.getAdapter(TypeToken.get(type));
    return new GsonResponseBodyConverter<>(gson, adapter);
  }

  @Override
  public Converter<?, RequestBody> requestBodyConverter(Type type,
      Annotation[] parameterAnnotations, Annotation[] methodAnnotations, Retrofit retrofit) {
    TypeAdapter<?> adapter = gson.getAdapter(TypeToken.get(type));
    return new GsonRequestBodyConverter<>(gson, adapter);
  }

再來看一下如何生成對象請求對象的併發出請求的
創建一個retrofit2 包下的OkhttpCall對象。這個call對象裏面有兩個引用一個是ServiceMath對象一個是okhttp3包下的Call對象。
最後看一下返回的serviceMath.callAdapter.adapt(okhttpcall)方法
會生成一個ExecuteCallbackCall對象(默認的CallAdapterFactory),通過這個對象調用enqueue方法會調用retrofit2裏面okhttpCall對象的enqueue方法,最終對調用okhttp3包下call 對象的enqueue方法。

數據轉換
在retrofit2包下的okhttpCall對象,enqueue方法會對okhttp包下Call返回的數據進行解析,解析類是servicemath對象的reaponseConvertor對象,然後將解析好的數據返回回來。

4、以及閱讀retrofit源碼的感受。
分析網絡框架可以從大的方面去着手,主要分爲三步。
1、如何創建請求數據。
2、如何創建請求對象和發起請求。
3、如何對請求數據的處理。

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章