Android 訪問網絡:方案三 OkHttp + Retrofit + RxJava

本文使用登錄場景來簡單介紹 Android 應用中使用 OkHttp + Retrofit + RxJava 訪問網絡的用法厘惦。

  • 數據交換協(xié)議 HTTP
  • 數據交換格式 JSON
  • HTTP 請求方法 POST

使用 HTTP 訪問網絡的準備工作鸵鸥,參見Android 訪問網絡:方案一 OkHttp一文訪問網絡的準備工作部分。

使用 OkHttp + Retrofit + RxJava 訪問網絡


1. 引入依賴

build.gradle(:app)

dependencies {
    ...
    implementation 'com.squareup.retrofit2:retrofit:2.9.0'
    implementation 'com.squareup.retrofit2:converter-gson:2.9.0'
    implementation 'com.squareup.retrofit2:adapter-rxjava3:2.9.0'

    implementation 'com.squareup.okhttp3:logging-interceptor:3.14.9'

    implementation 'io.reactivex.rxjava3:rxandroid:3.0.2'
}

2. 定義網絡訪問接口

創(chuàng)建 UserService 接口鸟雏,用來提供 User 模塊的網絡訪問服務。
UserService.java

public interface UserService {

    @POST("user/login")
    Single<Result<String>> login(@Body LoginParam loginParam);

}

Single 是 RxJava 中的一種可觀察對象類览祖。Retrofit 為我們創(chuàng)建該類的實例后孝鹊,即可調用 subscribe() 方法發(fā)起 HTTP 請求,然后在 SingleObserver 中處理請求結果展蒂。

有些關于 OkHttp + Retrofit + RxJava 的文章中在這里會使用 ObservableObserver又活。

它們兩者的區(qū)別如下:

  • Single 只發(fā)射一個值,或者一個錯誤通知锰悼。
  • Observable 可以發(fā)射 0 或多個值和一個結束通知柳骄,或者一個錯誤通知。

HTTP 請求場景可能需要處理的結果有兩種:一是請求成功箕般,順利和服務端交換了數據耐薯;二是請求失敗。

如果把處理 HTTP 請求結果比作削蘋果丝里,那么使用 Single 類似于使用水果刀曲初;而 Observable 更像是使用菜刀。

總的來說丙者,Single 就像是為這個場景量身打造的复斥,而 Observable 則更加通用。都能勝任這個任務械媒,至于選擇目锭,就看個人喜好吧评汰。

關于 Result 類和方法注解的介紹,參見Android 訪問網絡:方案二 OkHttp + Retrofit一文的使用 OkHttp + Retrofit 訪問網絡-2.定義網絡訪問接口部分痢虹。

3. 創(chuàng)建 Retrofit 實例

  1. 創(chuàng)建 OkHttp 實例被去,添加日志攔截器,以便調試奖唯。
OkHttpClient client = new OkHttpClient.Builder()
    .addInterceptor(new HttpLoggingInterceptor().setLevel(HttpLoggingInterceptor.Level.BODY))
    .build();
  1. 創(chuàng)建 Retrofit 實例惨缆,配置 baseUrl , 添加 ConverterFactory 和 CallAdapterFactory 。
Retrofit retrofit = new Retrofit.Builder()
    .baseUrl("http://192.168.43.218:8080/")
    .addConverterFactory(GsonConverterFactory.create())
    .addCallAdapterFactory(RxJava3CallAdapterFactory.create())
    .client(client)
    .build();

4. 創(chuàng)建 Service 實例

UserService userService = retrofit.create(UserService.class);

5. 創(chuàng)建 Single 實例

Single<Result<String>> single = userService.login(new LoginParam(userName, password));

由于這一步比較簡單丰捷,通常的寫法是和下一步連起來坯墨,將 Single 的實例作為匿名對象來使用。

userService.login(new LoginParam(userName, password))
    .subscribeOn(Schedulers.io())
    .observeOn(AndroidSchedulers.mainThread())
    .subscribe(new SingleObserver<Result<String>>() {...});

6. 向服務端發(fā)送 HTTP 請求

創(chuàng)建 SingleObserver 實例病往,用于處理網絡訪問結果捣染。

single.subscribeOn(Schedulers.io()).observeOn(AndroidSchedulers.mainThread()).subscribe(new SingleObserver<Result<String>>() {
    @Override
    public void onSubscribe(@NonNull Disposable d) {

    }

    @Override
    public void onSuccess(@NonNull Result<String> result) {
        
    }

    @Override
    public void onError(@NonNull Throwable e) {

    }
});
  • subscribeOn(Schedulers.io()) 在 IO 線程發(fā)送 HTTP 請求
  • observeOn(AndroidSchedulers.mainThread()) 在主線程處理請求結果
  • onSubscribe() 當即將發(fā)送請求時調用
  • onSuccess() 當請求成功時調用
  • onError() 當請求失敗時調用
    注:此處的成功和失敗是 HTTP 數據交換層面的意義。成功指的是 APP 和服務端順利交換了數據停巷。例如不論 APP 接收到的響應數據是{ "code": 600, "message": "登錄成功", "data": "token" } 還是 { "code": 701, "message": "密碼錯誤", "data": "" } 耍攘,都是請求成功,會執(zhí)行 onSuccess() 方法畔勤。當無法和服務端交換數據時蕾各,則會執(zhí)行 onError() 方法。

7. 在 SingleObserver 的 onSuccess() 中處理網絡訪問結果

@Override
public void onSuccess(@NonNull Result<String> result) {
    Toast.makeText(LoginActivity.this, result.message, Toast.LENGTH_SHORT).show();
    if (result.isSuccessful()) {
        Log.i(TAG, "token : " + result.data);
        // save token
        // start activity
    }
}


測試設備參數

  • 型號:vivo Y66L
  • 操作系統(tǒng):Funtouch OS 3.0(Android 6.0.1)

參考資料

  1. Single · ReactiveX 文檔中文翻譯
  2. ReactiveX : RxJava
  3. ReactiveX : RxAndroid

代碼

XuMeng-0 / android-study

最后編輯于
?著作權歸作者所有,轉載或內容合作請聯(lián)系作者
  • 序言:七十年代末庆揪,一起剝皮案震驚了整個濱河市式曲,隨后出現的幾起案子,更是在濱河造成了極大的恐慌嚷硫,老刑警劉巖检访,帶你破解...
    沈念sama閱讀 206,723評論 6 481
  • 序言:濱河連續(xù)發(fā)生了三起死亡事件,死亡現場離奇詭異仔掸,居然都是意外死亡脆贵,警方通過查閱死者的電腦和手機,發(fā)現死者居然都...
    沈念sama閱讀 88,485評論 2 382
  • 文/潘曉璐 我一進店門起暮,熙熙樓的掌柜王于貴愁眉苦臉地迎上來卖氨,“玉大人,你說我怎么就攤上這事负懦⊥厕啵” “怎么了?”我有些...
    開封第一講書人閱讀 152,998評論 0 344
  • 文/不壞的土叔 我叫張陵纸厉,是天一觀的道長系吭。 經常有香客問我,道長颗品,這世上最難降的妖魔是什么肯尺? 我笑而不...
    開封第一講書人閱讀 55,323評論 1 279
  • 正文 為了忘掉前任沃缘,我火速辦了婚禮,結果婚禮上则吟,老公的妹妹穿的比我還像新娘槐臀。我一直安慰自己,他們只是感情好氓仲,可當我...
    茶點故事閱讀 64,355評論 5 374
  • 文/花漫 我一把揭開白布水慨。 她就那樣靜靜地躺著,像睡著了一般敬扛。 火紅的嫁衣襯著肌膚如雪晰洒。 梳的紋絲不亂的頭發(fā)上,一...
    開封第一講書人閱讀 49,079評論 1 285
  • 那天舔哪,我揣著相機與錄音欢顷,去河邊找鬼。 笑死捉蚤,一個胖子當著我的面吹牛,可吹牛的內容都是我干的炼七。 我是一名探鬼主播缆巧,決...
    沈念sama閱讀 38,389評論 3 400
  • 文/蒼蘭香墨 我猛地睜開眼,長吁一口氣:“原來是場噩夢啊……” “哼豌拙!你這毒婦竟也來了陕悬?” 一聲冷哼從身側響起,我...
    開封第一講書人閱讀 37,019評論 0 259
  • 序言:老撾萬榮一對情侶失蹤按傅,失蹤者是張志新(化名)和其女友劉穎捉超,沒想到半個月后,有當地人在樹林里發(fā)現了一具尸體唯绍,經...
    沈念sama閱讀 43,519評論 1 300
  • 正文 獨居荒郊野嶺守林人離奇死亡拼岳,尸身上長有42處帶血的膿包…… 初始之章·張勛 以下內容為張勛視角 年9月15日...
    茶點故事閱讀 35,971評論 2 325
  • 正文 我和宋清朗相戀三年,在試婚紗的時候發(fā)現自己被綠了况芒。 大學時的朋友給我發(fā)了我未婚夫和他白月光在一起吃飯的照片惜纸。...
    茶點故事閱讀 38,100評論 1 333
  • 序言:一個原本活蹦亂跳的男人離奇死亡,死狀恐怖绝骚,靈堂內的尸體忽然破棺而出耐版,到底是詐尸還是另有隱情,我是刑警寧澤压汪,帶...
    沈念sama閱讀 33,738評論 4 324
  • 正文 年R本政府宣布粪牲,位于F島的核電站,受9級特大地震影響止剖,放射性物質發(fā)生泄漏腺阳。R本人自食惡果不足惜落君,卻給世界環(huán)境...
    茶點故事閱讀 39,293評論 3 307
  • 文/蒙蒙 一、第九天 我趴在偏房一處隱蔽的房頂上張望舌狗。 院中可真熱鬧叽奥,春花似錦、人聲如沸痛侍。這莊子的主人今日做“春日...
    開封第一講書人閱讀 30,289評論 0 19
  • 文/蒼蘭香墨 我抬頭看了看天上的太陽主届。三九已至赵哲,卻和暖如春,著一層夾襖步出監(jiān)牢的瞬間君丁,已是汗流浹背枫夺。 一陣腳步聲響...
    開封第一講書人閱讀 31,517評論 1 262
  • 我被黑心中介騙來泰國打工, 沒想到剛下飛機就差點兒被人妖公主榨干…… 1. 我叫王不留绘闷,地道東北人橡庞。 一個月前我還...
    沈念sama閱讀 45,547評論 2 354
  • 正文 我出身青樓,卻偏偏與公主長得像印蔗,于是被迫代替她去往敵國和親扒最。 傳聞我的和親對象是個殘疾皇子,可洞房花燭夜當晚...
    茶點故事閱讀 42,834評論 2 345

推薦閱讀更多精彩內容