gpt4 book ai didi

android - 验证匿名内部类中的模拟交互

转载 作者:行者123 更新时间:2023-11-28 20:40:30 25 4
gpt4 key购买 nike

我正在尝试在我的应用程序中测试我的 ViewModel,这是构造函数:

@Inject
public SearchUserViewModel(@Named("searchUser") UseCase searchUserUseCase) {
this.searchUserUseCase = searchUserUseCase;
}

在我的测试中,我创建了一个带有如下模拟的 SearchUserUseCase:

Observable error = Observable.error(new Throwable("Error"));
when(gitHubService.searchUser(MockFactory.TEST_USERNAME_ERROR)).thenReturn(error);

when(ObserverThread.getScheduler()).thenReturn(Schedulers.immediate());
when(SubscriberThread.getScheduler()).thenReturn(Schedulers.immediate());

searchUserUseCase = new SearchUserUseCase(gitHubService, SubscriberThread, ObserverThread);

在我的 ViewModel 类中,我有这个要测试的 fragment :

public void onClickSearch(View view) {
loadUsers();
}

private void loadUsers() {
if (username == null) {
fragmentListener.showMessage("Enter a username");
} else {
showProgressIndicator(true);
searchUserUseCase.execute(new SearchUserSubscriber(), username);
}
}

private final class SearchUserSubscriber extends DefaultSubscriber<SearchResponse> {

@Override
public void onCompleted() {
showProgressIndicator(false);
}

@Override
public void onError(Throwable e) {
showProgressIndicator(false);
fragmentListener.showMessage("Error loading users");
}

@Override
public void onNext(SearchResponse searchResponse) {
List<User> users = searchResponse.getUsers();
if (users.isEmpty()) {
fragmentListener.showMessage("No users found");
} else {
fragmentListener.addUsers(users);
}
}

}

最后在我的测试中我得到了这个:

@Test
public void shouldDisplayErrorMessageIfErrorWhenLoadingUsers() {
SearchUserViewModel searchUserViewModel = new SearchUserViewModel(searchUserUseCase);
searchUserViewModel.setFragmentListener(mockFragmentListener);
searchUserViewModel.setUsername(MockFactory.TEST_USERNAME_ERROR);
searchUserViewModel.onClickSearch(view);
verify(mockFragmentListener).showMessage("Error loading users");
}

我从 Mockito 得到这个错误:

Wanted but not invoked:
fragmentListener.showMessage(
"Error loading users"
);

我不确定这是否是一个好的测试,但我想以某种方式测试 SearchUserSubscriber。谢谢

编辑:我在这里发现了与此问题类似的问题:Can't verify mock method call from RxJava Subscriber (仍然没有回答)和这里:Verify interactions in rxjava subscribers .后一个问题类似,但不会在单独的类中执行订阅者(这发生在此处的 SearchUserUseCase 中)。

我还尝试了 RobolectricGradleTestRunner 而不是 MockitoJunitRunner 并更改为 Schedulers.io() 和 AndroidSchedulers.mainThread(),但我仍然遇到相同的错误。

尝试模拟 SearchUserUseCase 而不是 GitHubService(感觉更干净),但我不确定如何以这种方式测试订阅者,因为它作为参数传递给 UseCase 中的 void 方法 execute()。

public void execute(Subscriber useCaseSubscriber, String query) {
subscription = buildUseCase(query)
.observeOn(postExecutionThread.getScheduler())
.subscribeOn(threadExecutor.getScheduler())
.subscribe(useCaseSubscriber);
}

和 buildUseCase()

@Override
public Observable buildUseCase(String username) throws NullPointerException {
if (username == null) {
throw new NullPointerException("Query must not be null");
}
return getGitHubService().searchUser(username);
}

最佳答案

对我来说,添加一个 Observable.Transformer<T, T>如下:

void gatherData() {
service.doSomeMagic()
.compose(getSchedulerTransformer())
.subscribe(view::displayValue);
}

private <T> Observable.Transformer<T, T> getSchedulerTransformer() {
if (mTransformer == null) {
mTransformer = (Observable.Transformer<T, T>) observable -> observable.subscribeOn(Schedulers.io())
.observeOn(AndroidSchedulers.mainThread());
}

return mTransformer;
}

void setSchedulerTransformer(Observable.Transformer<Observable<?>, Observable<?>> transformer) {
mTransformer = transformer;
}

并设置Transformer。我刚刚通过了这个:

setSchedulerTransformer(observable -> {
if (observable instanceof Observable) {
Observable observable1 = (Observable) observable;
return observable1.subscribeOn(Schedulers.immediate())
.observeOn(Schedulers.immediate());
}
return null;
});

所以只需添加一个@Before测试方法并调用 presenter.setSchedulerTransformer它应该能够对此进行测试。如果您想了解更多详情,请查看 this回答。

关于android - 验证匿名内部类中的模拟交互,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/35599624/

25 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com