Retrofit和RxJava的优点有哪些在此就不赘述了,之前已经有数位大神在各个网站上发了若干文章,博主深感受益匪浅。 我在这里仅仅介绍一下我最近尝试的封装方法,至于为啥要封装,答:因为懒。。。
我们可以看一下使用 retrofit进行Http请求的代码:
okHttpClient = new OkHttpClient.Builder()
.addInterceptor(httpLoggingInterceptor)
.build();
retrofit = new Retrofit.Builder()
.baseUrl(baseUrl)
.addCallAdapterFactory(RxJavaCallAdapterFactory.create())
.addConverterFactory(GsonConverterFactory.create())
.client(okHttpClient)
.build();
retrofitMethod = retrofit.create(RetrofitMethod.class);
Call<List<User>> call = retrofitMethod.processList();
call.enqueue(new Callback<List<User>>() {
@Override
public void onResponse(Call<List<User>> call, Response<List<User>> response) {
if(response.body().size() > 0){
List<User> lt_userList = response.body();
Gson gson = new Gson();
String st_userList = gson.toJson(lt_userList);
Log.d("MainActivity", "result = " + st_userList);
tv_showText.setText(st_userList);
}else{
Log.d("MainActivity", "no data");
}
}
@Override
public void onFailure(Call<List<User>> call, Throwable t) {
Log.d("MainActivity", "failed");
}
});
当然,怎么可以少了build.gradle:
compile 'com.squareup.retrofit2:retrofit:2.1.0'
compile 'com.squareup.retrofit2:converter-gson:2.1.0'
compile 'com.squareup.retrofit2:adapter-rxjava:2.1.0'
compile 'com.squareup.okhttp3:okhttp:3.4.1'
compile 'com.squareup.okhttp3:logging-interceptor:3.4.1'
compile 'com.squareup.okhttp3:okhttp-urlconnection:3.4.1'
compile 'io.reactivex:rxjava:1.1.0'
compile 'io.reactivex:rxandroid:1.1.0'
好了,一次请求看着还不错,至少感觉比异步任务要好一些,不过如果我再请求一个Result这个model的List呢?那么第二段代码又要写一次,将里面所有的User换成Result即可,but,总有你恶心的那一天,而且如果结合RxJava后,你会发现那个长度更恶心。。。
RxJava中会有指定观察者、被观察者、订阅等,还有指定在某个线程进行操作,这些内容大同小异,可以封装起来,于是乎有了第一版封装:
public void processLists(Subscriber<List<User>> subscriber){
retrofitMethod.processLists()
.subscribeOn(Schedulers.io())
.unsubscribeOn(Schedulers.io())
.observeOn(AndroidSchedulers.mainThread())
.subscribe(subscriber);
}
RetrofitMethod.java
@GET("user/list/")
Observable<List<User>> processLists();
调用过程:
private void getLists(){
Subscriber<List<User>> subscriber = new Subscriber<List<User>>() {
@Override
public void onCompleted() {
Toast.makeText(RetrofitThree.this, "complete", Toast.LENGTH_SHORT).show();
}
@Override
public void onError(Throwable e) {
Toast.makeText(RetrofitThree.this, "error", Toast.LENGTH_SHORT).show();
Log.d("RetrofitThree", "error:" + e);
}
@Override
public void onNext(List<User> users) {
Gson gson = new Gson();
String st_userList = gson.toJson(users);
tv_resultThree.setText(st_userList);
}
};
HttpManager3.getInstanc().processLists(subscriber);
}
RxJava的订阅者中的方法主要有三个:onComplete(),当不再有新的onNext()发出时,触发onComplete()作为队列完结;onError(),事件队列异常,当它被触发时,队列自动终止,原则上讲onError()与onComplete()只能触发一个,并且是队列的最后一个;onNext(),回调的处理写在这里。
这次封装我们将关心的事件都放在明显的位置,准备做处理,将RxJava的一些设置封装了起来。但是细心的童鞋会发现:封装你妹啊!就封了一个方法!哥要调多个方法怎么办?!都封里面哥就疯了!!!
额,这个事情博主也考虑了,所以正确的姿势应该是这样的:
public void processList(Observable observable , Subscriber subscriber){
observable.subscribeOn(Schedulers.io())
.unsubscribeOn(Schedulers.io())
.observeOn(AndroidSchedulers.mainThread())
.subscribe(subscriber);
}
调用方法:
Subscriber<List<User>> subscriber = new Subscriber<List<User>>() {
@Override
public void onCompleted() {
Toast.makeText(RetrofitThree.this, "complete", Toast.LENGTH_SHORT).show();
}
@Override
public void onError(Throwable e) {
Log.d("RetrofitThree", "error" + e);
}
@Override
public void onNext(List<User> users) {
Toast.makeText(RetrofitThree.this, "ok", Toast.LENGTH_SHORT).show();
Gson gson = new Gson();
tv_resultThree.setText(gson.toJson(users));
}
};
HttpManager3.getInstanc().processList(retrofitMethod.processLists() , subscriber);
诸位现在感觉怎么样?这次封装的套路没变,只不过是同时接收了被观察者和订阅者(观察者),这样就不会十个方法封十次了。 博主赶脚这次不会被打死了。
细心的小盆友又会说啦,介个onComplete()和onError()每次处理的方法基本都一样啊,我就关心onNext()。好吧,应大家之邀,把onComplete()和onError()也封装起来吧:
public class NewSubscriber3<T> extends Subscriber<T> {
// 回调接口
private HttpOnNextListener3 mSubscriberOnNextListener;
// 弱引用防止内存泄露
private WeakReference<Context> mActivity;
private Context context;
public NewSubscriber3(HttpOnNextListener3 mSubscriberOnNextListener, Context context) {
this.mSubscriberOnNextListener = mSubscriberOnNextListener;
this.mActivity = new WeakReference<>(context);
this.context = context;
}
@Override
public void onCompleted() {
Toast.makeText(context, "subscriber completed", Toast.LENGTH_SHORT).show();
}
@Override
public void onError(Throwable e) {
Log.d("NewSubscriber3", "error:" + e);
}
@Override
public void onNext(T t) {
if (mSubscriberOnNextListener != null) {
mSubscriberOnNextListener.onNext(t);
}
}
}
interface:
public interface HttpOnNextListener3<T>{
void onNext(T t);
}
调用过程:
HttpOnNextListener3<List<User>> simpleOnNextListener = new HttpOnNextListener3<List<User>>() {
@Override
public void onNext(List<User> users) {
Toast.makeText(RetrofitThree.this, "ok3", Toast.LENGTH_SHORT).show();
Gson gson = new Gson();
tv_resultThree.setText(gson.toJson(users));
}
};
RetrofitMethod retrofitMethod = HttpManager3.getMethod();
NewSubscriber3<List<User>> newSubscriber3 =
new NewSubscriber3(simpleOnNextListener , this);
HttpManager3.getInstanc().processList(retrofitMethod.processLists() , newSubscriber3);
最后再奉上神秘的HttpManager3.java:
package com.example.administrator.mytest.Retrofit3;
import com.example.administrator.mytest.Config.JavaConfig;
import com.example.administrator.mytest.HttpClient.RetrofitMethod;
import com.example.administrator.mytest.model.User;
import java.util.List;
import rx.Observable;
import java.util.concurrent.TimeUnit;
import okhttp3.OkHttpClient;
import retrofit2.Retrofit;
import retrofit2.adapter.rxjava.RxJavaCallAdapterFactory;
import retrofit2.converter.gson.GsonConverterFactory;
import rx.Subscriber;
import rx.android.schedulers.AndroidSchedulers;
import rx.schedulers.Schedulers;
/**
* Created by Ly on 2017/1/3.
*/
public class HttpManager3 {
private volatile static HttpManager3 INSTANCE;
private static long DEFUALT_TIMEOUT = 5000;
private volatile static RetrofitMethod retrofitMethod;
//构造方法私有
private HttpManager3(){
}
private static RetrofitMethod Retro(){
//手动创建一个OkHttpClient并设置超时时间
OkHttpClient.Builder builder = new OkHttpClient.Builder();
builder.connectTimeout(DEFUALT_TIMEOUT, TimeUnit.SECONDS);
Retrofit retrofit = new Retrofit.Builder()
.client(builder.build())
.addCallAdapterFactory(RxJavaCallAdapterFactory.create())
.addConverterFactory(GsonConverterFactory.create())
.baseUrl(JavaConfig.kfb_baseUrl)
.build();
retrofitMethod = retrofit.create(RetrofitMethod.class);
return retrofitMethod;
}
//获取单例
public static HttpManager3 getInstanc(){
if(INSTANCE == null){
synchronized (HttpManager3.class){
if(INSTANCE == null){
INSTANCE = new HttpManager3();
}
}
}
return INSTANCE;
}
public static RetrofitMethod getMethod(){
if(retrofitMethod == null){
synchronized (Retro()){
if(retrofitMethod == null){
retrofitMethod = Retro();
}
}
}
return retrofitMethod;
}
public void processLists(Subscriber<List<User>> subscriber){
retrofitMethod.processLists()
.subscribeOn(Schedulers.io())
.unsubscribeOn(Schedulers.io())
.observeOn(AndroidSchedulers.mainThread())
.subscribe(subscriber);
}
public void processList(Observable observable , Subscriber subscriber){
observable.subscribeOn(Schedulers.io())
.unsubscribeOn(Schedulers.io())
.observeOn(AndroidSchedulers.mainThread())
.subscribe(subscriber);
}
}
博主的现学现卖到此告一段落,如有不足之处,还望大家指出~