android - 在分页库 v2 中使用 RxJava 时设置 Espresso 空闲资源
问题描述
我正在尝试在使用 Paging library v2 和 RxJava 时编写 Espresso 测试:
class PageKeyedItemDataSource<T>(
private val schedulerProvider: BaseSchedulerProvider,
private val compositeDisposable: CompositeDisposable,
private val context : Context
) : PageKeyedDataSource<Int, Character>() {
private var isNext = true
private val isNetworkAvailable: Observable<Boolean> =
Observable.fromCallable { context.isNetworkAvailable() }
override fun fetchItems(page: Int): Observable<PeopleWrapper> =
wrapEspressoIdlingResource {
composeObservable { useCase(query, page) }
}
override fun loadAfter(params: LoadParams<Int>, callback: LoadCallback<Int, Character>) {
if (isNext) {
_networkState.postValue(NetworkState.LOADING)
isNetworkAvailable.flatMap { fetchItems(it, params.key) }
.subscribe({
_networkState.postValue(NetworkState.LOADED)
//clear retry since last request succeeded
retry = null
if (it.next == null) {
isNext = false
}
callback.onResult(it.wrapper, params.key + 1)
}) {
retry = {
loadAfter(params, callback)
}
initError(it)
}.also { compositeDisposable.add(it) }
}
}
override fun loadInitial(
params: LoadInitialParams<Int>, callback: LoadInitialCallback<Int, Character>,
) {
_networkState.postValue(NetworkState.LOADING)
isNetworkAvailable.flatMap { fetchItems(it, 1) }
.subscribe({
_networkState.postValue(NetworkState.LOADED)
if (it.next == null) {
isNext = false
}
callback.onResult(it.wrapper, null, 2)
}) {
retry = {
loadInitial(params, callback)
}
initError(it)
}.also { compositeDisposable.add(it) }
}
}
这是我的wrapEspressoIdlingResource
:
inline fun <T> wrapEspressoIdlingResource(task: () -> Observable<T>): Observable<T> = task()
.doOnSubscribe { EspressoIdlingResource.increment() } // App is busy until further notice
.doFinally { EspressoIdlingResource.decrement() } // Set app as idle.
但它不会等到数据从网络传递过来。当我在数据传递之前 Thread.Sleep 时,Espresso 测试将通过,所以它与我的 Idling Resource 设置有关。
我相信它可能与 Paging 库有关,因为当我在没有 Paging 库的其他示例中使用 Observable 类型时,这种方法非常适用。
完整的源代码可在:https ://github.com/AliRezaeiii/StarWarsSearch-Paging
我错过了什么?
解决方案
我需要覆盖构建器上的 fetchDispatcher :
class BasePageKeyRepository<T>(
private val scheduler: BaseSchedulerProvider,
) : PageKeyRepository<T> {
@MainThread
override fun getItems(): Listing<T> {
val sourceFactory = getSourceFactory()
val rxPagedList = RxPagedListBuilder(sourceFactory, PAGE_SIZE)
.setFetchScheduler(scheduler.io()).buildObservable()
...
}
}
推荐阅读
- python - SQLAlchemy 如何在查询中加入多个模型
- java - Spring MVC异常处理
- google-cloud-platform - 如何创建没有外部 IP 地址的 Compute Engine 实例?
- javascript - 在返回之前在 Node.js 中等待
- javascript - 日期时间在 mac os -3 小时上无法正常工作
- mysql - 统计sql中的json标签
- regex - 从匹配中排除某些单词的正则表达式
- python - TwoSum 解决方案仅适用于一个输入
- javascript - “Multipart: Boundary not found”:Reactjs、Express、Multer 和 S3 的文件上传问题
- winapi - 使用 winapi 从扫描码获取字符的问题