dimanche 24 novembre 2019

Error writing tests using Mockito and async calls from Cloud Firestore

I'm trying to write some tests for my Android app using Mockito and I keep getting this error:

Wanted but not invoked: view.displayProfiles( [com.example.reconheca.model.Profile@1e800aaa, com.example.reconheca.model.Profile@185a6e9, com.example.reconheca.model.Profile@6f03482] ); -> at com.example.reconheca.view.ProfileListActivityPresenterTest.shouldPassProfileToView(ProfileListActivityPresenterTest.java:48) Actually, there were zero interactions with this mock.

These are my classes been called:

ProfileListActivityPresenterTest

private String usedId = "string";
private ArrayList<Profile> PROFILE_LIST = new ArrayList<>(Arrays.asList(new Profile(), new Profile(), new Profile()));
private Task<ArrayList<Profile>> task;
private ProfileListActivityPresenter presenter;

@Rule
public MockitoRule mockitoRule = MockitoJUnit.rule();

@Mock
ProfileFirestoreRepository profileRepository;

@Mock
ProfileListActivityView view;

@Before
public void setUp() {
    task = getTestTaskWithResult();
    presenter = new ProfileListActivityPresenter(view, profileRepository);
}

@Test
public void shouldPassProfileToView() {
    when(profileRepository.getProfilesFromUser(usedId)).thenReturn(task);
    presenter.loadProfiles(usedId);
    verify(view).displayProfiles(task.getResult());
}

@Test
public void shouldHandleNoProfile() {
    when(profileRepository.getProfilesFromUser(usedId)).thenReturn(task);
    presenter.loadProfiles(usedId);
    verify(view, never()).displayNoProfiles();
}

public Task<ArrayList<Profile>> getTestTaskWithResult() {
    TaskCompletionSource<ArrayList<Profile>> taskCompletionSource = new TaskCompletionSource<>();
    taskCompletionSource.setResult(PROFILE_LIST);
    return taskCompletionSource.getTask();
}

ProfileListActivityPresenter

private ProfileListActivityView view;
private ProfileFirestoreRepository profileFirestoreRepository;

public ProfileListActivityPresenter(ProfileListActivityView view, ProfileFirestoreRepository profileFirestoreRepository) {
    this.view = view;
    this.profileFirestoreRepository = profileFirestoreRepository;
}

public void loadProfiles(String userId) {
    Task<ArrayList<Profile>> task = profileFirestoreRepository.getProfilesFromUser(userId);

    task.addOnCompleteListener(new OnCompleteListener<ArrayList<Profile>>() {
        @Override
        public void onComplete(@NonNull Task<ArrayList<Profile>> task) {
            task.addOnSuccessListener(profiles -> {
                if (profiles.isEmpty()){
                    view.displayNoProfiles();
                } else {
                    view.displayProfiles(profiles);
                }
            })
            .addOnFailureListener(exception -> view.displayError(exception.getMessage()));
        }
    });
}

The method getProfilesFromUser return a task using Cloud Firestore.

Using the debug mode, I see that the code never execute the task.addOnCompleteListener and forward so displayProfiles never gets called. I can't figure it out what I'm doing wrong.

Aucun commentaire:

Enregistrer un commentaire