前面两篇文章已经大致介绍了 retrofit 以及实际在项目中的使用。
初探 Retrofit (入门) https://www.jianshu.com/p/8dc7cc4d0339
再见 Retrofit(实战) https://www.jianshu.com/p/22bc837b4ef9
这期再来聊聊 rxjava。为什么会来聊这个呢,因为看网上很多文章,谈到 retrofit 基本都会涉及 rxjava,仿佛是黏连在一起的东西,起初对他们都不了解,分别查询之后才知道,不是一个概念的。
在我看来 RxJava 其实是一种写法,思想,是更为抽象的一个概念,我理解为 Rx-Java,去看 Rx 官网的话,会发现原来 Rx 是个系列,还有 RxSwift,RxJs等。再看 retrofit 的 github 源码,你会发现有一个 retrofit-adapters 文件夹,里面有一个 rxjava2 文件夹(rxjava 文件夹可以忽略,我们直接用最新的),恍然大悟,原来 retrofit 是这样和 rxjava 扯上关系的,既然口子开在这里,那我们也不客气了,直接上。
「一开始我也在想,为什么非要将这两个凑一起呢,要凑一起的话怎么凑呢?这个口子就解决了怎么凑的问题。那为什么要凑一起呢,我想是因为 ReactiveX 这种设计,写起来比我们自己封装的优美许多,并且也确实能解决实际问题」
添加依赖
//for rxjava
implementation 'io.reactivex.rxjava2:rxjava:2.2.0'
//for rxandroid
implementation 'io.reactivex.rxjava2:rxandroid:2.1.0'
如果 rxjava 是用在 android 项目上,那么第二个依赖要加上。接着还需要加一个依赖,之后 retrofit 和 rxjava 就可以很好的结合了。
//rxjava adapter for retrofit
implementation 'com.squareup.retrofit2:adapter-rxjava2:2.4.0'
retrofit 配置
Retrofit.Builder reBuilder = new Retrofit.Builder()
.addConverterFactory(GsonConverterFactory.create())
.addCallAdapterFactory(RxJava2CallAdapterFactory.create()); //这里表示配置 rxjava 的适配器,这样 retrofit 就不再会用默认的适配器了。
开始改造
因为 rxjava 采用了观察者模式,所以整体思想是要有一个被观察者,一个观察者以及一个订阅关系。
被观察者 Observable 就是我们的请求方法。
public interface ApiServiceFactory {
// post 请求,入参有多个字段
@POST("你要用的接口地址")
Observable loginReq(@Body LoginReq req);
// post 请求,入参有一个或者多个字段
@POST("你要用的接口地址")
Observable checkVersion(@Body Map version);
// get 请求,用作下载文件
@GET
Observable getApk(@Url String url);
}
拿之前写的代码改造之后就是上面这样,唯一的不同就是返回类型不同。
那么观察者 Observer 又是什么呢?显然是请求的返回。
new Observer() {
@Override
public void onSubscribe(Disposable d) {
/**这个方法订阅的时候会触发,仅一次*/
Log.d("onSubscribe", "subscribe");
}
@Override
public void onNext(ResponseBean responseBean) {
/**这个方法会在结果成功的情况下触发,一次请求对应一次结果*/
Log.d("onNext", responseBean.toString());
}
@Override
public void onError(Throwable e) {
/**这个方法会在结果失败的情况下触发,一次请求对应一次结果*/
Log.d("onError", e.getMessage());
}
@Override
public void onComplete() {
/**这个方法会最后执行,表示请求完成*/
Log.d("onComplete", "Complete");
}
});
这是对原来的异步回调 callback 进行的改造,首先 observer 的回调要多一些,但是各个方法都有其含义,在相应的方法里做对应的处理就可以了。我的理解是,onSubscribe 和 onComplete 不用太关心,onNext 就相当于之前的 onResponse, onError 就相当于之前的 onFailure。
最后通过 onSubscribe() 方法订阅两者就可以了。
SampleRetrofitManager.getInstance().service.loginReq(request)
.subscribeOn(Schedulers.newThread()) //表示请求是在子线程
.observeOn(AndroidSchedulers.mainThread()) //表示回调是在主线程,这就是前面添加的第三个依赖的使用方法
.subscribe(new Observer() {
@Override
public void onSubscribe(Disposable d) {
Log.d("onSubscribe", "subscribe");
}
@Override
public void onNext(SampleModel sampleBean) {
Log.d("onNext", sampleBean.toString());
}
@Override
public void onError(Throwable e) {
Log.d("onError", e.getMessage());
}
@Override
public void onComplete() {
Log.d("onComplete", "Complete");
}
});
像这样就对之前 retrofit 的请求改造完成了。这里不仅实现了网络请求,同时还做了线程切换,耗时任务在子线程里做,UI 更新回调主线程。
那到底用了 rxjava 之后可以帮我们解决哪些问题或者改进哪些地方,暂且留到下期再来说说。