验证对mock的调用的间歇性错误

时间:2018-04-06 14:23:46

标签: java junit mockito executorservice

以下类在另一个线程上调用函数MyService::execute

public class Foo
{
    @Inject
    private MyService m_service;

    @Inject
    private ExecutorService m_executor;

    public void foo()
    {
        MyRequest myRequest = new MyRequest("bar");

        System.out.println("TP1");

        m_executor.execute( () ->
        {
            System.out.println("TP2");
            m_service.execute(myRequest);
            System.out.println("TP3");
         } );

        System.out.println("TP4");
    }
}

我创建了一些单元测试,用正确的参数检查executeMyService被嘲笑。

public class FooTests
{
    private final MyService m_myService = Mockito.mock(MyService.class);

    @Test
    public final void foo1()
    {
        final ExecutorService executor = Executors.newSingleThreadExecutor();
        InjectionBinder injectionBinder = new InjectionBinder(m_myService, executor);

        // some code that calls foo()

        ArgumentCaptor<MyRequest> argument = ArgumentCaptor.forClass(MyRequest.class);
        Mockito.verify(m_myService, Mockito.times(1)).execute(argument.capture());

        // check arguments
    }

    @Test
    public final void foo2()
    {
        final ExecutorService executor = Executors.newSingleThreadExecutor();
        InjectionBinder injectionBinder = new InjectionBinder(m_myService, executor);

        // some code that calls foo()

        ArgumentCaptor<MyRequest> argument = ArgumentCaptor.forClass(MyRequest.class);
        Mockito.verify(m_myService, Mockito.times(1)).execute(argument.capture());

        // check arguments
    }
}

测试在Windows和OSX上运行正常,但foo2经常在Linux上运行。

失败的原因是没有调用mock:

org.mockito.exceptions.verification.WantedButNotInvoked:
Wanted but not invoked:
myService.execute(<Capturing argument>);
-> at FooTests.foo2(#line number)
Actually, there were zero interactions with this mock.

但是我确实看到m_service.execute中对Foo的调用附近的打印报表。

我正在使用JUnit 4.12和Mockito 2.2.26。

我错过了什么?

修改

我已经弄明白了。有时,测试在另一个线程上安排MyService::execute之前运行完成。

在调用foo之后,在验证对MyService::execute的调用之前,在我的测试中添加了一个简短的等待来解决问题。

0 个答案:

没有答案
相关问题