我需要从本地存储请求,如果它为空,我应该请求服务并存储在数据库中,但如果数据库不为空,我应该忽略第二部分。我正在使用房间持久性数据库(可流动),我的意思是如果我存储在数据库中,我可以监听更改。我正在使用 concat,但零件的八分之一正在工作
val item1 = itemDao.loadItem(id)
val item2 = apiIcaSeResource
.fetchItem(offerId)
.toFlowable()
.doOnNext { item ->itemDao.saveItem(Item(...) }
Flowable.concat(item1, item2)
.subscribeOn(Schedulers.io())
.observeOn(AndroidSchedulers.mainThread())
.subscribe({
// items ->
}, {
Timber.e(it, "Error reading items")
})
@Query("SELECT * FROM offer WHERE id = :offerId")
fun loadItem( offerId: String): Flowable<Item>
@Insert(onConflict = OnConflictStrategy.REPLACE)
fun saveItem(items: Item)
@GET("item/{itemId}")
Single<Item> fetchItem(@Path("itemId") Long itemId);
@Query("SELECT * FROM offer WHERE id = :offerId")
fun loadItem( offerId: String): Flowable<Item>
像这样定义房间 DAO 时,如果一个项目不存在,Flowable
将不会发出任何内容。不会有onNext
事件。也称为Flowable
房间从不发出onComplete
。
Flowable.concat
等待第一个Flowable
发出onComplete
然后订阅第二个Flowable
并发出所有项目。
从 alpha5 开始,您可以将 Room 中的返回类型指定为 Maybe<Item>
以便检测数据库中是否存在现有项。另一种选择是将返回类型定义为 Flowable<List<Item>>
如果数据库中不存在该项,Room 将发出空列表。
如果将"房间"切换为:
@Query("SELECT * FROM offer WHERE id = :offerId")
fun loadItem( offerId: String): Flowable<List<Item>>
你可以做这样的事情(仅当数据库中有 0 个项目时才调用 API):
item1.flatMap { if(it.size == 0) item2 else Flowable.just(it) }
请注意,如果 API 调用中出现错误,这将结束流。检查onErrorXXX
运算符以解决此问题。