框架學習| Retrofit2.x(一)

開新坑辣!一直以爲本身框架了解的特別少,大多隻知其名而不知實現原理,然而幾乎每次面試都會被問及框架。因此頗有必要總結一些經常使用的框架,但願本身能堅持把這個『框架學習』系列的新坑填的厚實一點!android

先從網絡框架中大名鼎鼎的Retrofit開始吧,本篇先對Retrofit有個瞭解,目錄以下:

  • 概述
  • 使用方式

1.概述git

a.Retrofit是Square公司推出的一個基於RESTful風格的HTTP網絡框架。github

相關連接地址:面試

b.與OkHttp的關係:設計模式

是對OkHttp網絡請求框架的二次封裝,本質還是OkHttp。即網絡請求的工做本質上是由OkHttp完成,而Retrofit僅負責網絡請求接口的封裝。流程如圖:bash

  • App應用程序經過Retrofit請求網絡,其實是使用Retrofit接口層封裝請求參數、Header、Url等信息,以後由OkHttp完成後續的請求操做。
  • 在服務端返回數據以後,OkHttp將原始的結果交給Retrofit,Retrofit會根據用戶的需求對結果進行解析。
  • 經過使用大量的設計模式進行功能模塊的解耦,使得上面的過程進行得更加簡單和流暢。

c.其餘網絡框架簡介:服務器

  • AndroidAsynHttp:基於HttpClient,已經中止維護,Android5.0再也不使用HttpClient。
  • Volley:基於HttpUrlConnection,由谷歌官方推出,適合輕量級網絡交互,如數據傳輸量小的場景,而不適合大文件傳輸。

相比於上述兩種網絡框架,Retrofit具備的優勢網絡

  • 遵循Restful API設計風格,簡潔易用
  • 支持同步&異步網絡請求
  • 支持多種數據的解析&序列化格式(Gson、 Json、XML、 Protobuf)
  • 支持對RxJava支持
  • 註解化配置高度解耦、採用大量設計模式簡化使用

2.使用方式app

大體分紅八個步驟:框架

step1:添加Retrofit庫、OkHttp庫、數據解析器集成庫的依賴,並註冊網絡權限

在app文件包下的build.gradle中添加依賴,這裏用的是JSON數據解析器:

compile 'com.squareup.retrofit2:retrofit:2.4.0'
compile 'com.squareup.okhttp3:okhttp:3.10.0'
compile 'com.squareup.retrofit2:converter-gson:2.4.0'
複製代碼

在AndroidManifest.xml中註冊權限:

<uses-permission android:name="android.permission.INTERNET"/>
複製代碼

step2:建立接收服務器返回數據的類

請求後服務器會返回數據,須要根據返回數據的格式和解析方式(Json、XML等)來定義實體類Model。

假設有返回數據格式爲以下JSON,其中,若是用戶名和密碼匹配成功,則code值爲1,反之爲0:

{
  "code":1,
  "data":{
     "id":10001,
     "username":"Tom",
     "email":"888888888@qq.com",
     "tel":"18088888888"
  },
  "message":"success"
}
複製代碼

則對應的實體類UserInfoModel:

public class UserInfoModel {

    public int code;
    public UserInfo data;
    public String message;
    
    public static class UserInfo{
    
        public int id;
        public String username;
        public String email;
        public String tel;
    }
}
複製代碼

step3:建立用於描述網絡請求的接口

定義一個網絡請求的接口,接口函數裏要定義URL路徑請求參數返回類型。其中,須要使用註解來描述請求類型和請求參數。

public interface Interface {
  
    @GET("URL")
    Call<Model>  getCall(@Query("xxx") String xxx);
   
    // 用@GET("URL")聲明瞭URL路徑
    // 用getCall()接收網絡請求數據,並用註解@Query("xxx") 聲明瞭請求參數
    // 該方法會返回一個Retrofit的Call對象,這裏聲明瞭這個對象處理的數據類型爲自定義Model
}
複製代碼

在上例中,對應的UserMgrService接口以下,當發送請求參數爲Tom和123456時,請求將發送給的URL爲『login?username=Tom&pwd=123456』,並會返回以前定義的GSON數據:

public interface UserMgrService{
    
    @GET("login")
    Call<UserInfoModel> login(@Query("username") String username,@Query("pwd") String pwd);
}
複製代碼

經常使用的註解含義如圖:

這裏能夠發現,@GET和@Query搭配使用,@POST和@Field搭配使用。


step4:建立Retrofit對象並設置數據解析器

Retrofit retrofit = new Retrofit.Builder()
                .baseUrl("URL") //設置網絡請求的Url地址,注意以要以斜線(表明根目錄)結尾
                .addConverterFactory(GsonConverterFactory.create()) //設置數據解析器,這裏表示用的是JSON解析返回值
                .build();
複製代碼

經常使用的數據解析器如圖:


step5:生成接口對象

因爲是interface不是class,沒法直接調用內部方法,須要利用已建立的Retrofit對象去生成代理的接口對象。

UserMgrService service=retrofit.create(UserMgrService.class);
複製代碼

step6:調用接口方法返回Call對象

調用接口對象的方法,返回一個能夠執行網絡訪問的網絡工做對象。

Call<UserInfoModel> call=service.login("Tom","123456");
複製代碼

step7:發送網絡請求(異步 / 同步)

a.同步:調用Call對象execute(),返回結果是響應體。

//開線程進行網絡請求
new Thread(new Runable()){
    @Override
    pubblic void run(){
        Response<UserInfoModel> response=null;
        try{
           response=call.execute();
        }catch{
           e.printStackTrace();
        }
        //處理服務器返回的數據
    }
}.start();
複製代碼

b.異步:調用Call對象enqueue(),參數是一個回調。

//異步時,框架中已經封裝好數據轉換、線程切換的操做,無需手動開線程
call.enqueue(new CallBack<UserInfoModel>(){
    @Override
    public void onResponse(Call<UserInfoModel> call,Response<UserInfoModel> response){
        //處理服務器返回的數據
    }
    @Override
    public void onFailure(Call<UserInfoModel> call,Throwable t){
    }
});
複製代碼

step8: 處理服務器返回的數據

如今能夠去打印出返回結果:

Log.i("response","code:"+response.body().code);//結果爲"code:1"
複製代碼

下面給出官方給的simple demo,便於更好的理解Retrofit的使用步驟:

//step3:
public interface GitHub {
    @GET("/repos/{owner}/{repo}/contributors")
    Call<List<Contributor>> contributors(
        @Path("owner") String owner,
        @Path("repo") String repo);
  }

  public static void main(String... args) throws IOException {
    // step4:Create a very simple REST adapter which points the GitHub API.
    Retrofit retrofit = new Retrofit.Builder()
        .baseUrl(API_URL)
        .addConverterFactory(GsonConverterFactory.create())
        .build();

    // step5:Create an instance of our GitHub API interface.
    GitHub github = retrofit.create(GitHub.class);

    // step6:Create a call instance for looking up Retrofit contributors.
    Call<List<Contributor>> call = github.contributors("square", "retrofit");

    // step7:Fetch and print a list of the contributors to the library.
    List<Contributor> contributors = call.execute().body();
    
    //step8:
    for (Contributor contributor : contributors) {
      System.out.println(contributor.login + " (" + contributor.contributions + ")");
    } 
  }
複製代碼

實例這是一份很詳細的 Retrofit 2.0 使用教程(含實例講解)


以上,能夠看到,Retrofit可根據不一樣的接口定義,靈活地生成對應的網絡工做對象,而後利用這個對象去訪問網絡。它就像一個工廠,只提供產品,自己不處理網絡請求,而是讓產品去處理網絡請求。

下一篇將進行Retrofit的源碼分析~

相關文章
相關標籤/搜索