开发者

Simulating side effects of a mocked method

I have a method in a class that causes side effects to the method's parameter:

public void SideEffectsClass {
    public void doSomethingWithSideEffects(List<Object> list) {
        // do something to the list
    }
}

And this class being tested:

public void ClassUnderTest() {
   public List<Object> execute() {
       List<Object> results = new ArrayList<Object>();
       new SideEffectsClass().doSomethingWithSideEffects(results);
       return results;
   }
}

My test method using JMockit:

@Test
public void test() throws Exception
{
    // arrange
    new Expectations()
    {
        SideE开发者_如何转开发ffectsClass sideEffects;
        {
            new SideEffectsClass();
            sideEffects.doSomethingWithSideEffects((List<Object>) any);
            // I want to simulate that the List<Object> parameter has changed 
            // (has more elements, less elements, etc. after this method is called
        }
    };

    // act
    ClassUnderTest testClass = new ClassUnderTest();
    List<Object> results = testClass.execute();

    // assert
    Assert.assertEquals(myExpectedResults, results);
}


You can use a Delegate object to change an argument value:

    sideEffects.doSomethingWithSideEffects((List<Object>) any);
    result = new Delegate() {
        void delegate(List<Object> list) { list.add(new Object()); }
    };

If all you need is to verify that the doSomethingWithSideEffects methods was called, then the test could be written more simply as:

@Test
public void test(final SideEffectsClass sideEffects)
{
    List<Object> results = new ClassUnderTest().execute();

    assertEquals(myExpectedResults, results);

    new Verifications() {{
        sideEffects.doSomethingWithSideEffects((List<Object>) any);
    }};
}


As the test is trying to tell you, the side effects aren't part of the behavior of ClassUnderTest. Don't try to test that here. Based on the code you're showing, all you should be testing is that results is passed to doSomethingWithSideEffects() and that the same object is returned from execute(). Being unfamiliar with JMockit syntax, I can't tell you exactly how to write it.

Aside: I do recommend, however, that everyone using a tool like jMock, JMockit, or EasyMock should use Mockito instead if they can.

0

上一篇:

下一篇:

精彩评论

暂无评论...
验证码 换一张
取 消

最新问答

问答排行榜