Warning: file_get_contents(/data/phpspider/zhask/data//catemap/9/java/372.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Java 使用PowerMock和Mockito与模拟的合作者通过spy进行测试的方法_Java_Junit_Mocking_Mockito_Powermock - Fatal编程技术网

Java 使用PowerMock和Mockito与模拟的合作者通过spy进行测试的方法

Java 使用PowerMock和Mockito与模拟的合作者通过spy进行测试的方法,java,junit,mocking,mockito,powermock,Java,Junit,Mocking,Mockito,Powermock,试图找出做一些看起来很简单的事情的最佳方法:测试一个特定的方法是否正在被测试的类中对协作者进行调用。我将Mockito 1.9.5和PowerMock 1.5.1与JDK 6一起使用 一般的方法是通过Mockito spy设置部分模拟,通过PowerMock WhiteBox方法设置内部状态,然后调用我正在测试的方法:creatFoo 尽可能地简化代码,同时仍能理解我的要点。下面是正在测试的类: public class FooGate { BlackBox.Factory factor

试图找出做一些看起来很简单的事情的最佳方法:测试一个特定的方法是否正在被测试的类中对协作者进行调用。我将Mockito 1.9.5和PowerMock 1.5.1与JDK 6一起使用

一般的方法是通过Mockito spy设置部分模拟,通过PowerMock WhiteBox方法设置内部状态,然后调用我正在测试的方法:creatFoo

尽可能地简化代码,同时仍能理解我的要点。下面是正在测试的类:

public class FooGate {
    BlackBox.Factory factory;
    BlackBox.Bar bar;

    public void createFoo(Foo foo) {
        bar = factory.produce(BlackBox.Bar.class);

        bar.create(bbFoo);
    }
    ...
}
下面是一个不起作用的测试:

@RunWith(PowerMockRunner.class)
@PrepareForTest(FooGate.class)
public class FooGateTest {
    @Test
    public void test() {

        FooGate testGate = Mockito.spy(new FooGate());

        BlackBox.Factory mockfactory = mock(BlackBox.Factory.class);
        BlackBox.Bar mockBar = mock(BlackBox.Bar.class);

        WhiteBox.setInternalState(testGate, BlackBox.Factory, mockFactory);
        WhiteBox.setInternalState(testGate, BlackBox.Bar, mockBar);

        Foo foo = new Foo();
        foo.setSetting("x");

        doAnswer(new Answer<Void>() {
            public Void answer(InvocationOnMock invocation) {
                ... do stuff ...
            }
        }).when(mockBar).create(any(Foo.class));

        // NPE here: seems like bar is null in testGate.
        testGate.createFoo(foo);

        assertStuff(...);

    }
}
如果我移除白盒。设置。。。对于工厂,我得到工厂生产的NPE。所以,这似乎是可行的

但doAnswer显然不是。或者别的什么

当然,我也愿意使用其他方法来完成同样的任务,但我想知道我在这里遗漏了什么


注意:这似乎不是导入的问题,因此我省略了它们,但是如果您认为它们可能有用,我可以将它们包括在内。

我遇到的问题相当简单。在这个问题的第一个版本中也不可能看到

问题是当调用我通过WhiteBox.setInternalState设置的工厂上的Product时,该方法没有正确地存根,因此返回null。所以当我试图调用bar.create:NPE时,bar是空的

通过在FooGateTest中正确截取产品来修复:


。。。测试通过,没有错误。

您是否尝试过使用调试器运行,以查看对WhiteBox.setInternalState的调用是否真的达到了预期效果?请尝试以下操作并报告。1.不要监视被测试的类。在上述测试中,我看不出有任何理由这样做。2.将setter方法添加到被测试的类中,并删除WhiteBox的使用。@DavidWallace我这样做了。没有setInernalStatemockFactory,我在工厂得到了NPE。这不重要。@JohnB 1。不管有没有间谍,不管有没有嘲弄;同样的结果。2.BlackBox.Factory和.Bar是第三方类。没有理由将它们设置为这个类的使用者,所以我不希望为它们创建setter只是为了测试。我的观点是添加setter只是为了看看这是否解决了问题。这不是一个长期的解决方案,但可能会为您指明正确的方向。
when(mockfactory.produce((Class)anyObject())).thenReturn(mockBar);