使用 RxAndroid MVP Retrofit 修改回调

Modify callbacks with RxAndroid MVP Retrofit

我使用 MVP 架构和 Retrofitcallbacks 有一段时间了。我想用 RxJava/Android 替换我的回调,但我似乎无法理解应该如何完成。

我有拦截器(Interactor)的接口:

    public interface FoodInterceptor extends MvpInterceptor {
    /*void getFoodList(RestCallback<FoodListResponse> callback);*/

    Observable getFoodList(Consumer<FoodListResponse> foodListResponseConsumer, Consumer<Throwable> error);
}

然后是拦截器实现:

    public class FoodInterceptorImpl implements FoodInterceptor {

    @Inject
    ApiService mApiService;
    @Inject
    ErrorUtils mErrorUtils;
    @Inject
    SchedulerProvider mSchedulerProvider;
    @Inject
    CompositeDisposable mCompositeDisposable;

    @Inject
    public FoodInterceptorImpl() {
        super();
    }

    @Override
public Observable<FoodListResponse> getFoodList(Consumer<FoodListResponse> foodListResponseConsumer, Consumer<Throwable> throwable) {
    mApiService.getFoodList()
            .subscribeOn(mSchedulerProvider.backgroundThread())
            .observeOn(mSchedulerProvider.mainThread())
            .subscribe(foodListResponse -> Log.d("TAG", "FoodResponse: " + foodListResponse),
                    throwable1 -> Log.d("TAG", "Throwable: " + throwable));

    return ?;
}

    @Override
    public void unbind() {

    }

    /*@Override
    public void getFoodList(final RestCallback<FoodListResponse> callback) {
        mApiService.getFoodList().enqueue(new Callback<FoodListResponse>() {
            @Override
            public void onResponse(Call<FoodListResponse> call, Response<FoodListResponse> response) {
                if (response.isSuccessful()) {
                    Result<FoodListResponse> result = new Result<>();
                    FoodListResponse foodListResponse = response.body();
                    result.setData(foodListResponse);
                    callback.onSuccess(result);
                } else {
                    mRestError = mErrorUtils.parseResponse(response);
                    Log.d("Test", "Error: " + mRestError.getMessage());
                }

            }

            @Override
            public void onFailure(Call<FoodListResponse> call, Throwable t) {

            }
        });

    }*/

    /*@Override
    public void cleanup() {

    }*/

}

在注释代码中您可以看到我将如何使用回调来完成它,但是 Rx 要求我 return Observable。我该怎么做?我如何通知演示者数据已提取?

演示者界面:

@PerActivity
public interface FoodPresenter<V extends FoodView, I extends FoodInterceptor> extends MvpPresenter<V, I> {
    void renderFoods();
}

主持人:

    public class FoodPresenterImpl<V extends FoodView, I extends FoodInterceptor>
        extends BasePresenter<V, I> implements FoodPresenter<V, I> {

    @Inject
    public FoodPresenterImpl(I mvpInterceptor,
                             SchedulerProvider schedulerProvider,
                             CompositeDisposable compositeDisposable) {
        super(mvpInterceptor, schedulerProvider, compositeDisposable);
    }



 @Override
public void renderFoods() {
    getMvpView().showProgress(true);
    getInterceptor().getFoodList(foodListResponse -> {
        if (!isViewAttached()) {
            return;
        }
        getMvpView().renderFoods(foodListResponse.getFoodList().getFoodItemList());
        getMvpView().showProgress(false);
    }, throwable -> {
        if (!isViewAttached()) {
            return;
        }
        getMvpView().showProgress(false);
    });
}

    /*@Override
    public void renderFoods() {
        getMvpView().showProgress(true);
        getInterceptor().getFoodList(new RestCallback<FoodListResponse>() {
            @Override
            public void onSuccess(Result<FoodListResponse> result) {
                if (!isViewAttached()) {
                    return;
                }
                getMvpView().renderFoods(result.getData().getFoodList().getFoodItemList());
                getMvpView().showProgress(false);
            }

            @Override
            public void onFailure(RestError error) {

            }
        });
    }*/
}

让我稍微分解一下你的逻辑:

  1. renderFoods 在演示者中被调用
  2. Presenter 调用拦截器,因此它将获取 api 和 return 结果
  3. 拦截器调用 mApi.getFoodList()(它应该 return Observable)并且 itnterceptro 订阅结果。我将使用 lambda,因此可能会遗漏部分:

    mApi.getFoodList()
      .subscribeOn(Schedulers.io()) // main work will be on io thread
      .observeOn(AndroidSchedulers.mainThread()) // result will be passed to main thread
      .subscribe((result, throwable) -> {
         // it's like your calback, the job are done 
         // and you get result in result parameter, 
         // and if error occurs, result will be null 
         // and throwable parameter has an cause
         // so, here you can apply errorUtils on result, check the throwable, 
         // or pass result to your presenter
      });
    

希望对您有所帮助!