I am using creating an application using mapreduce2 and testing the same using MRUnit 1.1.0. In one of the tests, I am checking the output of a reducer which puts the 'current system time' in it's output. I.e. at the time the reducer executes, the timestamp is used in context.write()
to be written along with the rest of the output. Now even though I use the same method to find the system time in the test method as the one I use in the reducer, the times calculated in both are generally a second apart, like 2016-05-31 19:10:02
and 2016-05-31 19:10:01
. So the output in the two turns out to be different, example:
test_fe01,2016-05-31 19:10:01
test_fe01,2016-05-31 19:10:02
This causes an assertion error. I wish to ignore this difference in timestamps, so the tests pass if the rest of the output apart from the timestamp is matched. I am looking for a way to mock the method used for returning the system time, so that a hardcoded value is returned, and the reducer and the test both use this mocked method during the test. Is this possible to do? Any help will be appreciated.
Best Regards
EDIT: I have already tried Mockito's spy functionality in the my test:
MClass mc = Mockito.spy(new MClass());
Mockito.when(mc.getSysTime()).thenReturn("FakeTimestamp");
However, this gives a runtime error:
org.mockito.exceptions.misusing.MissingMethodInvocationException:
when() requires an argument which has to be 'a method call on a mock'.
For example:
when(mock.getArticles()).thenReturn(articles);
Also, this error might show up because:
1. you stub either of: final/private/equals()/hashCode() methods.
Those methods *cannot* be stubbed/verified.
2. inside when() you don't call method on mock but on some other object.
3. the parent of the mocked class is not public.
It is a limitation of the mock engine.
The method getSysTime()
is public and static and class MClass
is public and doesn't have any parent classes.