我会这样测试主持人:
class MostPopularPresenter @Inject constructor(val mostPopularUseCase: MostPopularUseCase)
: Presenter<MostPopularView>() {
fun requestMostPopular(page: Int, update: Boolean) {
if (page <= 6)
mostPopularUseCase.execute(MostPopularObserver(), MostPopularUseCase.Params.createQuery(page, 15, update))
}
inner class MostPopularObserver : DisposableSingleObserver<MostPopularModel>() {
override fun onSuccess(t: MostPopularModel) {
this@MostPopularPresenter.view?.populateRecyclerList(t)
}
override fun onError(e: Throwable) {
this@MostPopularPresenter.view?.showError()
}
}
}
我有一个问题,如何 mock 观察者,并迫使它在成功时抛出错误或返回值。我正在使用模拟/ junit。有人可以指出我该如何实现吗?也许我的代码无法测试?
最佳答案
observer
是一个不应真正测试的对象。虽然有人说,出于某种原因,您还应该测试第三方库,以确保它不会破坏您的代码,但是它已经由第三方开发人员进行了测试。版本之间。
因此,如果您不测试observer
...您如何测试代码?简而言之,您真正需要测试的是演示者本身。在observer
内部运行的代码是演示者的一部分。因此,与其模拟observer
而不是模拟useCase
:
test useCaseFails() {
val usecase = // mock use case
when(usecase.execute(...))
.thenAnswer(/* receive the observer as first parameter
and make it emit an error */)
val presenter = ...
presenter.requestMostPopular(...)
// assert that presenter.view?.showError has been called
}
另一种方法(至少这是我通常的编码方式)是使
useCase
返回observable
并在presenter
中订阅它:class MostPopularPresenter @Inject constructor(val mostPopularUseCase: MostPopularUseCase)
: Presenter<MostPopularView>() {
private var lateinit observer : Disposable
fun requestMostPopular(page: Int, update: Boolean) {
if (page <= 6)
disposable = mostPopularUseCase.execute(MostPopularUseCase.Params.createQuery(page, 15, update))
.subscribe(t -> view?.populateRecyclerList(t),
e -> view?.showError())
}
}
这样,您可以轻松模拟
useCase
,从而返回可以控制的Subject
:test useCaseFails() {
val usecase = // mock use case
val subject = PublishSubject()
when(usecase.execute(...))
.thenReturn(subject)
val presenter = ...
presenter.requestMostPopular(...)
subject.emitError(...) // <- pseudocode
// assert that presenter.view?.showError has been called
}
关于unit-testing - 如何测试观察者?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/45045610/