Mockito: Mock private field initialization
Solution 1:
Mockito comes with a helper class to save you some reflection boiler plate code:
import org.mockito.internal.util.reflection.Whitebox; //... @Mock private Person mockedPerson; private Test underTest; // ... @Test public void testMethod() { Whitebox.setInternalState(underTest, "person", mockedPerson); // ... } Copy
Update: Unfortunately the mockito team decided to remove the class in Mockito 2. So you are back to writing your own reflection boilerplate code, use another library (e.g. Apache Commons Lang), or simply pilfer the Whitebox class (it is MIT licensed).
Update 2: JUnit 5 comes with its own ReflectionSupport and AnnotationSupport classes that might be useful and save you from pulling in yet another library.
Solution 2:
Pretty late to the party, but I was struck here and got help from a friend. The thing was not to use PowerMock. This works with the latest version of Mockito.
Mockito comes with this org.mockito.internal.util.reflection.FieldSetter
.
What it basically does is helps you modify private fields using reflection.
This is how you use it:
@Mock private Person mockedPerson; private Test underTest; // ... @Test public void testMethod() { FieldSetter.setField(underTest, underTest.getClass().getDeclaredField("person"), mockedPerson); // ... verify(mockedPerson).someMethod(); } Copy
This way you can pass a mock object and then verify it later.
Here is the reference.
Solution 3:
In case you use Spring Test try org.springframework.test.util.ReflectionTestUtils
ReflectionTestUtils.setField(testObject, "person", mockedPerson); Copy
Solution 4:
I already found the solution to this problem which I forgot to post here.
@RunWith(PowerMockRunner.class) @PrepareForTest({ Test.class }) public class SampleTest { @Mock Person person; @Test public void testPrintName() throws Exception { PowerMockito.whenNew(Person.class).withNoArguments().thenReturn(person); Test test= new Test(); test.testMethod(); } } Copy
Key points to this solution are:
- Running my test cases with PowerMockRunner:
@RunWith(PowerMockRunner.class)
- Instruct Powermock to prepare
Test.class
for manipulation of private fields:@PrepareForTest({ Test.class })
- And finally mock the constructor for Person class:
PowerMockito.mockStatic(Person.class);
PowerMockito.whenNew(Person.class).withNoArguments().thenReturn(person);
Solution 5:
Following code can be used to initialize mapper in REST client mock. The mapper
field is private and needs to be set during unit test setup.
import org.mockito.internal.util.reflection.FieldSetter; new FieldSetter(client, Client.class.getDeclaredField("mapper")).set(new Mapper()); Copy
Credits
This article follows the attribution requirements of Stack Overflow and is licensed under CC BY-SA 3.0.
Taken from : https://localcoder.org/mockito-mock-private-field-initialization