I'm trying to mock Lucenes IndexReader.close() to do nothing.
I thought this should work...
IndexReader reader = Mockito.mock(IndexReader.class);
Mockito.stubVoid(reader).toReturn().on().close(); // old approach
Mockito.doNothing().when(reader).close(); // new approach
but both result in the unit test calling the actual, real close method and ultimately causing a null pointer exception.
What have I missed?
As the javadoc indicates, close() is a final method. And Mockito can't mock final methods.
Related
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 using Mockito to mock a method in the same class for which I am writing test. I have seen other answers on SO (Mocking method in the same class), but probably I am misunderstanding them, since I running into issues.
class Temp() {
public boolean methodA(String param) {
try {
if(methodB(param))
return true;
return false;
} catch (Exception e) {
e.printStackTrace();
}
}
}
My Test method:
#Test
public void testMethodA() {
Temp temp = new Temp();
Temp spyTemp = Mockito.spy(temp);
Mockito.doReturn(true).when(spyTemp).methodB(Mockito.any());
boolean status = temp.methodA("XYZ");
Assert.assertEquals(true, status);
}
I however get the expection printed out because definition of methodB gets executed.
My understanding is definition of methodB would get mocked by using spyTemp. However that does not appear to be the case.
Can someone please explain where I am going wrong?
The first issue is that you have to use spyTemp object to expect something from Mockito. Here it is not the same as test. spyTemp is wrapped by the Mockito object temp.
Another issue is that you stub only methodB(), but you are trying to run methodA(). Yes in your implementation of methodA() you call methodB(), but you call this.methodB(), not spyTemp.methodB().
Here you have to understand that mocking would work only when you call it on the instance of temp. It's wrapped by a Mockito proxy which catches your call, and if you have overriden some method, it will call your new implementation instead of the original one. But since the original method is called, inside it you know nothing about Mockito proxy. So your "overriden" method would be called only when you run spyTemp.methodB()
This should work:
Mockito.doReturn(true).when(spyTemp).methodB(Mockito.any());
boolean status = spyTemp.methodA("XYZ");
You created a spy and mocked methodB(). That is correct! But you called methodA() on the original object. To get the correct result call it on the spy
boolean status = spyTemp.methodA("XYZ");
Note the following from Mockito documentation:
Mockito does not delegate calls to the passed real instance, instead
it actually creates a copy of it. So if you keep the real instance and
interact with it, don't expect the spied to be aware of those
interaction and their effect on real instance state. The corollary is
that when an unstubbed method is called on the spy but not on the
real instance, you won't see any effects on the real instance.
This is referring specifically to your situation. You keep a reference to temp and then call its methodA. Mockito is not spying on that instance at all; it's spying on spyTemp. So the normal methodB is called.
Note that you should avoid partial mocks altogether for new code.
I'm trying to understand how you can mock static methods, specifically from the static Files.class.
Basically, whenever this line executes:
Files.newInputStream(this.getPathObj(), StandardOpenOption.READ);
I want it to just return an object that is an instance of an InputStream.
The is my class with the static method I'm trying to mock.
public class JavaFileInput{
private Path path;
public JavaFileInput(Path path){
this.path = path;
}
public InputStream getInputStream() throws IOException {
return Files.newInputStream(this.getPathObj(), StandardOpenOption.READ);
}
public Path getPathObj() {
return this.path;
}
}
This is some "psuedo-ish" unit test code that obviously doesn't work, but I hope it portrays the idea of what I'm trying to accomplish.
#Mock(name="path")
private Path mockedPath = Mockito.mock(Path.class);
#InjectMocks
private JavaFileInput javaFile_MockedPath;
#Before
public void testSetup(){
javaFile_MockedPath = new JavaFileInput(mockedPath);
MockitoAnnotations.initMocks(this);
}
#Test
public void getNewInputStreamTest(){
//Setup
Mockito.when(Files.newInputStream(mockedPathObj, StandardOpenOption.Read)).thenReturn(new InputStream());
//Test
InputStream outputValue = javaFile_MockedPath.getInputStream();
//Validate
assertTrue(outputValue instanceof InputStream);
}
Does this make any sense? Has anyone ever had to do something similar? Any help would be greatly appreciated.
Thanks for your time!
I'm not clear what value your JavaFileInput provides. However, to test static methods you can look at PowerMock.
I came across the same problem: I have (own) code which modifies symlinks using nio.Files.
For testing my code without having to prepare and access the file system, I had to write an own mockable wrapper class around these functions.
Not so nice though that the nio JSR didn't consider this use case by defining an official interface and providing a non-static (=injectable) way for accessing Files. Mockito was known long before this..
Instead of using Mockito or PowerMock, you may also use a NIO2 implementation that work in memory:
memoryfilesystem
jimfs
While this won't solve all case (or let say it, it won't answer your attempt at mocking a static method) or allow you to create flawed InputStream (for example, one that would return an error when reading N bytes), this may suit your use case.
Also you ask if your case make any sense:
//Setup
Mockito.when(Files.newInputStream(mockedPathObj, StandardOpenOption.Read)).thenReturn(new InputStream());
//Test
InputStream outputValue = javaFile_MockedPath.getInputStream();
//Validate
assertTrue(outputValue instanceof InputStream);
You are testing that outputValue is indeed an instance of InputStream, which the compiler already does for you: outputValue is already an instance of InputStream, therefore asserting it is an instance of InputStream will never fails and your test is not checking what you want to check.
You'd best to test that outputValue is exactly the same instance as one returned, using a mock rather than new InputStream for example:
InputStream is = mock(InputStream.class);
Mockito.when(Files.newInputStream(mockedPathObj, StandardOpenOption.Read)).thenReturn(is);
InputStream outputValue = javaFile_MockedPath.getInputStream();
assertTrue(outputValue == is);
With standard Mockito, you can't mock static methods -- and I would question your reasons for doing so.
What do you seek to test by mocking the newInputStream method? You are merely creating a tautology -- that your method returns what you told it to return. And instanceof InputStream is a tautology as well.
It would make more sense to mock JavaFileInput to test another class that depends on it (perhaps by using a ByteArrayInputStream with sample data).
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);
I have to throw an IOException using Mockito for a method, which is reading an input stream like given below. Is there any way to do it?
public void someMethod() {
try {
BufferedReader in = new BufferedReader(new InputStreamReader(inputStream));
firstLine = in.readLine();
} catch(IOException ioException) {
// Do something
}
...
}
I tried mocking like
BufferedReader buffReader = Mockito.mock(BufferedReader.class);
Mockito.doThrow(new IOException()).when(buffReader).readLine();
but didn't work out :(
You're mocking a BufferedReader, but your method doesn't use your mock. It uses its own, new BufferedReader. You need to be able to inject your mock into the method.
It seems that inputStream is a field of the class containing this method. So you could mock the inputStream instead and make it throw an IOException when its read() method is called (by the InputStreamReader).
You can't mock BufferedReader here since it's being created inside the method.
Try mocking inputStream and throwing the exception from InputStream.read() instead.
The way that I would recommend is to have an extra class that looks after the creation of the BufferedReader. This class has just one method, with no actual logic in it, so it doesn't need any unit tests.
public class BufferedReaderFactory{
public BufferedReader makeBufferedReader(InputStream input) throws IOException{
return new BufferedReader(new InputStreamReader(input));
}
}
Now, add a private field of type BufferedReaderFactory to the class that you're testing, along with a means of injecting it - either a setter method or an alternate constructor. In the standard constructor for your class, instantiate a BufferedReaderFactory and set the field accordingly. In your someMethod(), call the makeBufferedReader() method on the field, instead of using new.
Your class is much more testable; because now, you can write a test that injects a mocked BufferedReaderFactory to the object that you're testing, before calling someMethod(). On that mock, you can stub the makeBufferedReader method to throw the exception that you want.
Please add a comment if you want me to go into more detail on any of the steps above. You might also like to read my post on mocking object creation on the Mockito wiki; which is closely related to this.
But the most important message is that making your classes testable is really important, and you will reap the benefits of doing so many times over.