I want to do an unit test that verifies if function1()
or function2()
were called. I haven't work with callbacks before, can you give me any idea about how to do it?
public void sendData(HttpService service, Document userData) {
Call<String> call = service.updateDocument(getId(), userData);
call.enqueue(new Callback<String>() {
@Override
public void onResponse(Call<String> call, Response<String> response) {
function1(response.code());
}
@Override
public void onFailure(Call<String> call, Throwable t) {
function2();
}
});
}
To do this, we'll need to switch your Retrofit interface implementation, that you use to make calls with a mock, and do some fake responses taking advantage of Mockito ArgumentCaptor class. Proceed with the test by right clicking the test class and hitting run. And that's it.
Retrofit - probably the most popular networking client in Android development. Basically it allows to create HTTP client in an interface - you just add annotation with HTTP method, relative or absolute path and proper request is constructed.
Retrofit uses two different callback methods for the two possible outcomes of a network requests: either a failure or a successful request. Retrofit will call the appropriate callback method depending on the result. If the request was successful, Retrofit will also pass you the response of the server.
You register a callback with a class when you create it, and you have a method that communicates back via that callback. Here’s our class. To test this we want to test that the method passes the right result to the callback. We could use an anonymous function with an assert inside, but that test would pass even if the callback was never called.
In my opinion the power of Retrofit comes from call and converter adapter factories - instead of relying on built-in types (such as retrofit2.Call) you can add RxJava call adapter and framework would find a way to convert Call<T> into rx Single<T>. Unfortunately we won't have direct access to Call.request () method then!
The JUnit framework never executes the code in the CallBack functions because the main thread of execution terminates before the response is retrieved. You can use CountDownLatch as shown below: This test sample may be helpful too. My advice isn't to perform testing for the API responses in the android app. There are many external tools for this.
However, that callback gets invoked by fs after its file read is complete, and since we’ll be mocking fs for our unit tests, how do we test that code?
I couldn't try, but it should work. Maybe you have to fix generic type
casting errors like mock(Call.class);
.
@Test
public void should_test_on_response(){
Call<String> onResponseCall = mock(Call.class);
doAnswer(invocation -> {
Response response = null;
invocation.getArgumentAt(0, Callback.class).onResponse(onResponseCall, response);
return null;
}).when(onResponseCall).enqueue(any(Callback.class));
sendData(....);
// verify function1
}
@Test
public void should_test_on_failure(){
Call<String> onResponseCall = mock(Call.class);
doAnswer(invocation -> {
Exception ex = new RuntimeException();
invocation.getArgumentAt(0, Callback.class).onFailure(onResponseCall, ex);
return null;
}).when(onResponseCall).enqueue(any(Callback.class));
sendData(....);
// verify function2
}
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With