How to mock a method call inside another method - java

Here is my code:
`public class Service {
callSomeService(ContextTpye1 c1,Parameter p){
//do something here
ContextTpye2 c2 = constructContext(c1,p);
if(c2.timeout()){
c2.audit();
}
}
}`
In the unit test, the Service, Parameter and ContextTpye1 are initialized. Is it possible to only mock c2.audit()? I wanna it to doNothing here. Thanks.

So the way I would attack the problem assuming constructContext(c1,p) is public is to when testing the Service class is to spy on the Service allowing you to mock the constructContext(c1,p) and returning a mock of ContextType2.
public class ServiceTest
{
private Service service = Mockito.spy(new Service());
private ContextType2 c2 = Mockito.mock(ContextType2.class);
#Test
public void testCallSomeService()
{
Mockito.when(service.constructContext(Mockito.eq(ContextType1.class), Mockito.eq(Parameter.class))).thenReturn(c2);
Mockito.when(c2.timeout()).thenReturn(true);
Mockito.when(c2.audit()).doNothing();
service.callSomeService(new ContextType1(), new Parameter());
}
}

Related

Mockito.spy() instance returns null when invoking real method

I want to test a service class.
class Service {
public List<A> mainMethodToTest() {
//calling another method to get some values
List<A> list = getImportantValues();
process list;
return list;
}
public getimportantValues() {
return new List<A>();
}
}
I want to test this service class method 'mainMethodToTest()' using Mockito and mock the call to getimportantValues() method.
Here is the test class I wrote.
class TestService {
private Service service;
#Before
public void setup() {
service = Mockito.spy(new Service);
}
#Test
public void testMainMethodToTest() {
Mockito.doReturn(new List<A>()).when(service).getimportantValues();
Assert.assertNotNull(service.mainMethodToTest()); /// this call throws NullPointerException because somehow it is not treating the service as a real instance of the Service object but a mock.
}
}
The last call in Assert to method 'mainMethodToTest()' throws NullPointer because it takes the service as null and not an instance.
Can someone please help me to understand what am I doing wrong in here.
TIA

How can I test if a method was called on an object created inside the method to be tested

Is it possible to test that the "innerMethod" was called without modifying the Class class?
I need to make a unit test in a separate class both scenario of the "someCondition".
The problem is that the method is void so I cannot make use of the return type. The only way would be to check if the "innerMethod" was called.
I was thinking to use Mokito verify but this method is called inside a method on an object created at runtime.
Any suggestion is most welcome.
public class Class {
public void outerMethod(outerObj) {
if(someCondition) {
Object innerObj = new Object();
innerObj.innerMethod(outerObj);
} else {
//other code
}
}
You can achieve that with the use of Mockito::times and Mockito::verify methods.
test setup would be as follows:
#InjectMocks
private SomeService service;
#Mock
private SomeHelper helper;
and then test that some method from the helper has been involved in the following manner:
#Test
public void testInnerHasBeenCalledOnce() throws Exception {
service.outherMethodName(someParam);
Mockito.verify(helper, Mockito.times(1)).innerMethodName(someParamSecond);
}

Is it possible to verify tested object method call with Mockito?

I' ve got some business logic class:
public class SomeService {
public void doFirst() {}
public void doSecond() {
doFirst();
}
}
and test for it:
public class SomeServiceTest {
private SomeService service;
#Before
public void setUp() {
service = new SomeService();
}
#Test
public void doSecond_someCondition_shouldCallFirst() {
// given
...
// when
service.doSecond();
//then
how to verify doFirst() was called?
}
}
How to verify doFirst() was called not on mock, but real service?
I wonder why you want to test, what method your method under tests invoke. Sounds pretty much like whitebox testing to me.
In my opinion, you want to verify the outcome of the invocation and not the way to get there, as this might easily change (i.e. when refactoring).
So if the outcome of doSecond() is the same as doFirst() you could write a test for doFirst() and use the same test (i.e. set of assertions) for testing doSecond().
But if you really want to test, whether doFirst() has been invoked by doSecond() you could wrap your service in a spy and then call the verification on the spy:
//given
SomeService service = new SomeService();
SomeService spy = Mockito.spy(service);
//when
spy.doSecond();
//then
verify(spy).doFirst();
It sounds like you want to avoid the real doFirst being called in your test? if so, try this...
//given
boolean firstCalled = false;
SomeService fakeService = new SomeService {
#Override
public void doFirst() {
firstCalled = true;
}
}
//when
fakeService.doSecond();
// then
assertTrue(firstCalled);
This testing/mocking technique is called 'subclass and override' for obvious reasons.

How to mock a method call within a method for which i am writing junit test

Could someone help me with mocking a method call within a method
my code is like :
public class Service {
public List<Bean> Filter(Bean bean){
List<Bean> Filtered_List = getUtilityService.getBeanList();
//Do something
return beanList;
}
}
Now i want to write test case for Service class . How can i mock :
List Filtered_List = getUtilityService.getBeanList(); and set values in it.
The clean solution is to extract UtilityService to a field and pass a mock to the constructor.
public class Service {
private UtilityService utilityService;
public Service(UtilityService utilityService) {
this.utilityService = utilityService;
}
public List<Bean> Filter(Bean bean){
List<Bean> filteredList = utilityService.getBeanList();
//Do something
return beanList;
}
}
You can also introduce a UtilityServiceFactory and have a utilityServiceFactory field in the Service.
public class Service {
private UtilityServiceFactory utilityServiceFactory;
public Service(UtilityServiceFactory utilityService) {
this.utilityServiceFactory = utilityServiceFactory;
}
public List<Bean> Filter(Bean bean){
List<Bean> filteredList = utilityService.create().getBeanList();
//Do something
return beanList;
}
}
If getUtilityService is located in Service class, there is also a dirty solution: partial mock. But I do not recommend it. It's better to refactor your code and use one of previous approaches.
EDIT:
Constructor injection with #InjectMocks is not the best idea but here you are:
import static org.assertj.core.api.Assertions.assertThat;
import static org.mockito.BDDMockito.given;
//other imports
#RunWith(MockitoJUnitRunner.class)
public class ServiceTest {
#Mock
UtilityService utilityService;
#InjectMocks
Service service = new Service(null);
#Test
public void shouldFilterBeans() throws Exception {
//given
given(utilityService.getBeanList()).willReturn(asList(new Bean()));
//when
List<Bean> result = service.filter(new Bean());
//then
assertThat(result).hasSize(1); //probably you want to check something else
}
}
to test a method including its own parameter and return value, like the Filter method in your code, it's enough to just pass a Bean instance to it, and then assert the returned List<Bean> object equals to your expected result. generally, for this kind of method, i think it's no need to use mock frameworks.
but if you really want to test the getUtilityService().getBeanList() method call, you should refactor your code:
addfield UnitilityService service and its corresponding setter method in your class Service
in your unit test code, inject a mocked service using the setter method to the object under test and given a returning value for its getBeanList() method, then invoke your Filter method, finally, verify the method call. for the detailed implementation, you can refer the answer of #woru.

Unit testing a fluent interface with Mockito

I want to mock the DAO interface used in the builder pattern as shown below. However when I run the test below it passes indicating that my mock object is never called. What am I doing wrong?
public class DBContent {
...
public static class Builder {
DAO dao = new DAO();
...
public Builder callInsert() {
...
long latest = dao.insert();
...
}
}
...
}
#RunWith(MockitoJUnitRunner.class)
public class DBContentTest {
#Mock
DAO dao;
#Test
public void test() {
when(dao.insert()).thenReturn(1111L);
DBContent db = DBContent.db()
.callInsert()
.callInsert()
.callInsert()
.build();
verifyZeroInteractions(dao);
}
}
Use PowerMockito instead. There you can define that whenever you have a call to a constructor of DAO, return my mocked object instead of returning actual DAO object.
Please refer this to learn how to use PowerMockito.

Categories

Resources