I have a situation where first argument of method findUser is something I cant mock Session.get(), So it will throw exception but still I want mock findUser. Any clue guys how to do this. I am using Mockito here.
eg.
Emp emp = findUser(Session.get(), "Admin");
Note Where Session isn't a static class. It is a static variable of the same class.
There is a library called PowerMockito --> https://www.baeldung.com/intro-to-powermock . You should be able to mock your Session varg as a mock or spy and handle the return get(). This should then allow you to mock your findUser method passing in the argument types to be expected. Cheers!
Related
On the first screenshot you can see my test class. This class is annotated with #ExtendWith({MockitoExtension.class}) and also the tested service is annotated with #InjectMocks. On the second screenshot you can see the tested service.
Why does Mockito uses the long supplier in both cases?
Mockito uses different strategies when injecting mocks in this order:
Constructor injection
Property setter injection
Field injection
Field injection will not work in your example, since the service's fields are declared final.
Since the fields are declared final and the code snippet you showed does not have a field initializer, I assume that you have a constructor with the Supplier args. E.g.
public SomeService(Supplier<String> stringSupplier, Supplier<Long> longTimeSupplier) {
this.stringSupplier = stringSupplier;
this.longTimeSupplier = longTimeSupplier;
}
Thus Mockito will try the constructor injection, find the constructor with the two Supplier parameters and tries to resolve the arguments.
Mockito then finds the two Supplier mocks in the test, but it can not see the generic type due to type erasure. Thus Mockito sees the constructor like this:
public SomeService(Supplier stringSupplier, Supplier longTimeSupplier)
Mockito can also not decide which Supplier to use based on the parameter name, because the normal Java reflection API does not provide that information. So the name of the mocks, will not be taken into account.
There are libraries like paranamer that read the bytecode and extract the debug information to read the parameter names, but Mockito doesn't use that libs.
Thus Mockito just injects the first matching mock which is Supplier<String> stringSupplier in your case. Even your issues is related to generics, Mockito would also act the same way when you have two parameters of the same type that are not generic.
I assumed that you have a constructor that takes the two Supplier. So you can just invoke it in your test's before.
#BeforeEach
public void setup() {
service = new SomeService(stringSupplier, longSupplier);
}
If you can not access the constructor, e.g. it has package scope, you need to invoke it using reflection and set the accessible property to true
#BeforeEach
public void setup() throws Exception {
Constructor<SomeService> constructor = SomeService.class.getConstructor(Supplier.class, Supplier.class);
constructor.setAccessible(true);
service = constructor.newInstance(stringSupplier, longSupplier);
}
PS If you want to remove the final, make sure that the mocks are either named after the fields in the service longTimeSupplier vs. longSupplier or you use #Mock(name = "longTimeSupplier").
I am trying to mock class instance and then return the mock object when we call the instance function but in result, it makes an actual call to function.
Here is my code:
AuthenticationSessionModel authSessionCookie =
new AuthenticationSessionManager(session)
.getCurrentAuthenticationSession(realm, client, tabId);
and my test code is:
AuthenticationSessionManager spyAuthSessionManager =
Mockito.spy(new AuthenticationSessionManager(session));
doReturn(authenticationSessionModel)
.when(spyAuthSessionManager)
.getCurrentAuthenticationSession(any(), any(), anyString());
It makes an actual call to getCurrentAuthenticationSession() and returns me Null Pointer Exception
In the test, you create a spy, and stub some behaviour.
But you don't use that spy in the code under test.
Instead, in the code under test you create a new AuthenticationSessionManager.
You need to restructure your code and:
create AuthenticationSessionManager outside of object under test.
pass it to object under test. Constructor is the first thing that comes to mind.
With these changes, it becomes trivial to substitute a real AuthenticationSessionManager with a spy in a test.
I am trying to mock a class with Mockito that has a method which chains an interface. The class is mocked successfully but when it calls the interface a null pointer is thrown. The code looks as below:
mock = Mockito.mock(MyProcess.class);
process = mock.getProcess()
.getService() //Interface throwing null exception
.startProcessInstanceByKey("String argument");
I got this solution and tried to follow the example on the page below but its not working: https://static.javadoc.io/org.mockito/mockito-core/2.13.0/org/mockito/Mockito.html#RETURNS_DEEP_STUBS
Foo mock = mock(Foo.class, RETURNS_DEEP_STUBS);
// note that we're stubbing a chain of methods here: getBar().getName()
when(mock.getBar().getName()).thenReturn("deep");
// note that we're chaining method calls: getBar().getName()
assertEquals("deep", mock.getBar().getName());
The example above is not working
You need to mock the retuning Service, too. All external dependencies of you classes need to be mocked and if you doesn´t do this you get null.
processMock = Mockito.mock(MyProcess.class);
serviceMock= Mockito.mock(Service.class);
Mockito.doReturn(serviceMock).when(processMock).getService();
Mockito.doReturn(<VALUE>).when(serviceMock).startProcessInstanceByKey("String argument");
You need to mock every step with external values - this is how it works.
I am new to Mockito, I am trying to verify the attributes of an object which gets created inside a method.
pseudo code below:
class A{
...
public String methodToTest(){
Parameter params = new Parameter(); //param is basically like a hashmap
params.add("action", "submit");
return process(params);
}
...
public String process(Parameter params){
//do some work based on params
return "done";
}
}
I want to test 2 things:
when I called methodToTest, process() method is called
process() method is called with the correct params containing action "submit"
I was able to verify that process() is eventually called easily using Mockito.verify().
However trying to check that params contains action "submit" is very difficult so far.
I have tried the following but it doesn't work :(
BaseMatcher<Parameter> paramIsCorrect = new BaseMatcher<Parameter>(){
#Overrides
public boolean matches(Object param){
return ("submit".equals((Parameter)param.get("action")));
}
//#Overrides description but do nothing
}
A mockA = mock(A);
A realA = new A();
realA.methodToTest();
verify(mockA).process(argThat(paramIsCorrect))
Any suggestion ?
If you have got verify() to work, presumably it is just a case of using an argument matcher to check the contains of params.
http://docs.mockito.googlecode.com/hg/org/mockito/Mockito.html#3
The example given in the above docs is verify(mockedList).get(anyInt()). You can also say verify(mockedList).get(argThat(myCustomMatcher)).
As an aside, it sounds like you are mocking the class under test. I've found that this usually means I haven't thought clearly about either my class or my test or both. In your example, you should be able to test that methodToTest() returns the right result irrespective of whether or not it calls process() because it returns a String. The mockito folk have lots of good documentation about this sort thing, particularly the "monkey island" blog: http://monkeyisland.pl/.
Just pass Parameter in as a constructor argument to a constructor of the class A, then use a mocked instance/implementation of Parameter in your test and verify on the mock. That is how it is normally done - you separate your classes and compose them using constructor injection, that enables you to pass in mocks for testing purposes (it also allows rewiring the application and exchanging some commons a lot easier).
If you need to create Parameter on every function invocation you should use a factory that creates Parameter instances and pass that in. Then you can verify on the factory as well as the object created by the factory.
I want to mock a constructor into method.
public String generaID() {
GeneraIDParaEntidadCliente aux = new GeneraIDParaEntidadCliente(nombre, registro);
entidad.setID(aux.generaID);
}
In my test I want do something like this :
when(new GeneraIDParaEntidadCliente(anyString(), any(Entidad.class)).thenReturn(generaIdMock)
but give me this error org.mockito.exceptions.misusing.InvalidUseOfMatchersException:
Any idea why?
UPDATE: since since version 3.5.0, Mockito can do this without PowerMockito.
You can use PowerMock to mock constructors.
If you can't use PowerMock for some reason, the most workable solution is to inject a factory to whatever class contains this method. You would then use the factory to create your GeneraIDParaEntidadCliente object and mock the factory.
There are a couple of ways of doing this, described in my article on the Mockito wiki
Copying answer from duplicate:
Mockito can now mock constructors (since version 3.5.0) https://javadoc.io/static/org.mockito/mockito-core/3.5.13/org/mockito/Mockito.html#mocked_construction
try (MockedConstruction mocked = mockConstruction(Foo.class)) {
Foo foo = new Foo();
when(foo.method()).thenReturn("bar");
assertEquals("bar", foo.method());
verify(foo).method();
}
you can send mocked objects as paramemters to your class constructor, form example:
// define you object
public MainClassObj instanceClass;
// mock input parameter
MYClassObj mockedObj = Mockito.mock(MYClassObj.class);
// call construvtor with mocked parameter
instanceClass = new instanceClass(mockedObj);