需求

有这样一个列表数据,它包含了商店+订单的信息,获取订单列表时,订单实体中会包含商店的 ID,而列表显示时需要商店的名称和 logo,这时候就需要进行嵌套串行网络请求了。

关键词

flatMap 、缓存 、Retrofit、RxJava

动手

(1)使用 Retrofit 定义网络接口

// RemoteService.java
// 请求订单信息
@POST("/order/v1/order_history")
Single<List<OrderResponse>> queryOrderList(@Body FetchOrderHistoryRequest request);
// 请求商店信息
@POST("/store/v1/store_query")
Single<StoreResponse> queryStore(@Body StoreQueryRequest request);

(2)使用 DataManager 管理数据

// DataManager.java
// 请求订单信息
public Single<List<OrderResponse>> queryOrderList(String status) {
FetchOrderHistoryRequest request = new FetchOrderHistoryRequest();
request.setStatus(status);
return mRemoteService.queryOrderList(request);
} // 请求商店信息,并缓存 5min,如果不作缓存可能导致多次重复请求同一数据
public static final int DEFAULT_CACHE_TIME_MILLIS = 5 * 60 * 1000; // 5min public Single<StoreResponse> queryStore(String storeId) {
String storeKey = PrefConstant.getStoreKey(storeId);
String storeJson = mMemberPref.getString(storeKey, null);
Single<StoreResponse> storeSingle;
if (!TextUtils.isEmpty(storeJson)) {
storeSingle = Single.just(Json.fromJson(storeJson, StoreResponse.class));
} else {
StoreQueryRequest request = new StoreQueryRequest();
request.setId(storeId);
storeSingle = mRemoteService.queryStore(request)
.doOnSuccess(storeResponse -> mMemberPref.put(storeKey,
Json.toJson(
storeResponse),
DEFAULT_CACHE_TIME_MILLIS));
}
return storeSingle;
}

注:

  1. mMemberPref 是我写的一个使用 SharedPreferences 进行数据缓存的类,详情查看 Pref.java

(3)多次FlatMap

dataManager.queryOrderList(status)
.flatMapObservable((Function<List<OrderResponse>, ObservableSource<OrderResponse>>) Observable::fromIterable)
.flatMap((Function<OrderResponse, ObservableSource<OrderHolder>>) orderResponse -> {
OrderHolder orderHolder = new OrderHolder();
orderHolder.setOrder(orderResponse);
return dataManager.queryStore(orderResponse.getStoreId())
.flatMapObservable((Function<StoreResponse, ObservableSource<OrderHolder>>) storeResponse -> {
orderHolder.setStore(storeResponse);
return Observable.just(orderHolder);
});
})
.toList()
.observeOn(AndroidSchedulers.mainThread())
.subscribeOn(Schedulers.io())
.subscribe(new SingleObserver<List<OrderHolder>>() {
@Override
public void onSubscribe(Disposable d) {
disposable = d;
} @Override
public void onSuccess(List<OrderHolder> orderHolders) {
if (orderHolders != null && !orderHolders.isEmpty()) {
getMvpView().showOrderList(orderHolders);
} else {
getMvpView().showEmpty();
}
} @Override
public void onError(Throwable e) {
Timber.e(e);
getMvpView().showError();
}
});
}

说明:

  1. 第一次 flatMapObservable ,将 List<OrderResponse> 转为 ObservableSource<OrderResponse>;
  2. 第二次 flatMap,将 OrderResponse 转为 ObservableSource<OrderHolder>;
  3. 第三次 flatMapObservable ,将 StoreResponse 合并到 OrderHolder,再转为ObservableSource<OrderHolder>。

使用 RxJava 进行嵌套串行网络请求的一种方法的更多相关文章

  1. iOS 串行网络请求。。。待研究

    nsurlsession 和 nsurlconnection 能实现吗? 手动实现的关键点在哪里? 我这里说的串行网络请求,指的是第一个网络请求不返回数据,第二个网络请求就不能开始. AFNetwor ...

  2. Retrofit2+Rxjava+OkHttp的使用和网络请求

    Retrofit2+Rxjava+OkHttp的使用和网络请求 https://blog.csdn.net/huandroid/article/details/79883895 加入Rxjava 如果 ...

  3. Oracle多行记录合并的几种方法

    今天正好遇到需要做这个功能,顺手搜了一下网络,把几种方法都列出来,方便以后参考. 1 什么是合并多行字符串(连接字符串)呢,例如: SQL> desc test; Name Type Nulla ...

  4. 【MySQL】锁——查看当前数据库锁请求的三种方法 20

    MySQL提供了查看当前数据库锁请求的三种方法:1. show  full  processlist命令  观察state和info列 2. show engine  innodb status\G ...

  5. php发送post请求的三种方法示例

    本文分享下php发送post请求的三种方法与示例代码,分别使用curl.file_get_content.fsocket来实现post提交数据,大家做个参考. php发送post请求的三种方法,分别使 ...

  6. php发送get、post请求的6种方法代码示例

    本文主要展示了php发送get.post请求的6种方法的代码示例,分别为使用file_get_contents .fopen.fsockopen.curl来发送GET和POST请求,代码如下: 方法1 ...

  7. sql语句实现行转列的3种方法实例

    sql语句实现行转列的3种方法实例 一般在做数据统计的时候会用到行转列,假如要统计学生的成绩,数据库里查询出来的会是这样的,但这并不能达到想要的效果,所以要在查询的时候做一下处理,下面话不多说了,来一 ...

  8. kotlin for android----------MVP模式下(OKHttp和 Retrofit+RxJava)网络请求的两种实现方式

    今天要说的干货是:以Kotlin,在MVP模式下(OKHttp和 Retrofit+RxJava)网络请求两种实现方式的一个小案例,希望对大家有所帮助,效果图: Retrofit是Square公司开发 ...

  9. 学习RxJava+Retrofit+OkHttp+MVP的网络请求使用

    公司的大佬用的是这一套,那我这个菜鸟肯定要学习使用了. 我在网上找了很多文章,写的都很详细,比如 https://www.jianshu.com/u/5fd2523645da https://www. ...

随机推荐

  1. Codeforces Gym101170I:Iron and Coal(建多幅图+多次BFS)***

    题目链接 题意 有n个点,其中有m个点是铁矿,k个点是煤,从1号点出发,你可以派一些士兵跑向不同的点,问占领至少一个铁矿和一个煤的时候,最少需要占领多少个点. 思路 建两幅图,其中一幅是正向边,一幅是 ...

  2. vue中修改子组件样式

    一.问题叙述 项目里需要新添加一个表单页面,里面就只是几个select,这个几个select是原本封装好的组件,有自己原本的样式,而这次的原型图却没有和之前的样式统一起来,需要微调一下,这里就涉及到父 ...

  3. 【JavaScript】深入理解call,以及与apply、bind的区别

    一.call call有两个妙用 1.继承(我前面的文章有提到用call实现call继承,有兴趣可以看下.https://www.cnblogs.com/pengshengguang/p/105476 ...

  4. springboot+redis实现session共享

    1.场景描述 因项目访问压力有点大,需要做负载均衡,但是登录使用的是公司统一提供的单点登录系统,需要做session共享,否则假如在A机器登录成功,在B机器上操作就会存在用户未登录情况. 2. 解决方 ...

  5. CAD2014学习笔记-图纸布局和打印输出

    基于 虎课网huke88.com CAD教程 图纸设计规范:施工图 封面设计:地点.名称.设计人 目录设计:施工图编号.名称.意义.对应页数.注释.图号序号:包括平面.立面.大样图.施工图 设计说明/ ...

  6. infiniband 网卡驱动安装

    硬件:Mellanox InfiniBand,主要包括 HCA(主机通道适配器)和交换机两部分软件:CentOS 6.4MLNX_OFED_LINUX-2.1-1.0.0-rhel6.4-x86_64 ...

  7. KafKa 发消息到Storm

    通过kafka客户端发送数据,由KafkaSpout进行接收消息,传输到ConsumerBolt进行实时数据处理. maven依赖 <dependencies> <!-- https ...

  8. Hadoop值Partition分区

    分区操作 为什么要分区? 要求将统计结果按照条件输出到不同文件中(分区).比如:将统计结果按 照手机归属地不同省份输出到不同文件中(分区) 默认 partition 分区 /** 源码中:numRed ...

  9. ehcache的使用 Shiro与Ehcache的结合(附:EhcacheUtils)

    ehcache 缓存的使用 合理的使用缓存会极大的提高程序的运行效率.切记:缓存请勿滥用. 配置ehcache与Shiro shiro初识请查看该文章 https://blog.csdn.net/py ...

  10. git pull 出现non-fast-forward的错误

    1.git pull origin daily_liu_0909:liu_0909 出现non-fast-forward的错误,证明您的本地库跟远程库的提交记录不一致,即 你的本地库版本需要更新2.g ...