Search code examples
javajmockit

Verify method in constructor was called


I have a constructor that calls a method, like this:

public Foo(boolean runExtraStuff) {
    if (runExtraStuff){
        doExtraStuff();
    }
}

The doExtraStuff() method is running some additional commands that are not easily mocked themselves (things like database checks to initialize some variables). Perhaps it would be better for the constructor to not do this, but this is the code I have to work with at the moment.

I would like to create a unit test to make sure that doExtraStuff() is called when the boolean runExtraStuff is true and does not run when the boolean is false. I am using JMockit.

However, I'm not sure how to make this happen. Normally I would use a Verifications on a mocked object, but since I am testing the constructor, I can't use a mocked object in this way. So how can I verify that a method within a constructor was called?


Solution

  • It's easy enough, even if it requires partial mocking:

    @Test
    public void runsSetupWhenRequestedOnFooInitialization()
    {
        // Partially mocks the class under test:
        new Expectations(Foo.class) {};
    
        final Foo foo = new Foo(true);
    
        // Assuming "setup" is not private (if it is, use Deencapsulation.invoke):
        new Verifications() {{ foo.setup(); }};
    }
    
    @Test
    public void doesNotRunSetupWhenNotRequestedOnFooInitialization()
    {
        new Expectations(Foo.class) {};
    
        final Foo foo = new Foo(false);
    
        new Verifications() {{ foo.setup(); times = 0; }};
    }
    

    Of course, it would probably be better to avoid mocking in a case like this; instead, the test should check the state of the object through getters or other available methods, if at all possible.