9.12.11

Mocking-out a Singleton

It may happen that you have to use some legacy Singleton class. And of course you want to create a test double for it, when writing your unit tests.
For this use case, EasyMock is not sufficient, so something stronger is needed: PowerMock. With this testing framework, you can mock-out final classes, static methods, private constructors etc.

Mandatory steps:
  • @RunWith(PowerMockRunner.class) - must be provided on class level
  • @PrepareForTest(MySingleton.class) - also on class level defining the class you want to power-mock
  •  PowerMock.mockStatic(MySingleton.class); -  enables static mocking

The rest of the unit test is done using the EasyMock API, e.g. :

...
import org.powermock.api.easymock.PowerMock;
import static org.easymock.EasyMock.*;

@RunWith(PowerMockRunner.class)
@PrepareForTest(MySingleton.class)
public class ClassUsingSingletonTest {

    @Test
    public void returnsTheSumOfTwoIntegers() throws Exception {
        PowerMock.mockStatic(MySingleton.class);

        MySingleton singletonMock = createMock(MySingleton.class);
        expect(MySingleton.getInstance())   
              .andReturn(singletonMock); 
        expect(singletonMock.doSomeLegacyStuff(anyInt()))
              .andReturn(true);
       
        PowerMock.replay(MySingleton.class);
        replay(singletonMock);

        ClassUsingSingleton classUnderTest =
                    new ClassUsingSingleton();
        int result = classUnderTest.addTwoNumbers(5, 5);
        assertEquals(10, result);
       
        verify(singletonMock);
        PowerMock.verify(MySingleton.class);
    }
}


2 comments: