如何使来自另一个线程的JUnit测试失败

l3zydbqr  于 2022-11-11  发布在  其他
关注(0)|答案(2)|浏览(124)

考虑以下测试代码:

@Test
public void test() throws InterruptedException {
    var latch = new CountDownLatch(1);

    Executors.newSingleThreadExecutor().execute(() -> {
        latch.countDown();
        Assert.fail("Doesn't fail the test");
    });

    latch.await();
}

它打印异常,但传递。
线程“池-1-线程-1”java.lang中出现异常。Assert错误:未通过位于org.junit.Assert.fail(Assert.java:89)的MyTest.lambda$test$0(MyTest.java:55)的测试,该测试位于java.base/java.util.concurrent。线程池执行程序运行工作程序(线程池执行程序. java:1128)位于java.base/java.util.concurrent。线程池执行程序$Worker.run(线程池执行程序. java:628)位于java.base/java.lang。线程运行程序(线程. java:834)
我尝试过设置自定义未捕获的异常处理程序setUncaughtExceptionHandler((t, e) -> Assert.fail(e.getMessage())),但这没有帮助。

pokxtpni

pokxtpni1#

您可以使用两个线程都可以访问的外部状态来完成此操作。

private volatile boolean failed  = false;

    @Test
    public void test() throws InterruptedException {
        var latch = new CountDownLatch(1);

        Executors.newSingleThreadExecutor().execute(() -> {
            failed = true;//or false depending on the use case
            latch.countDown();

        });

        latch.await();
        if(failed){
            Assert.fail("Doesn't fail the test");
        }
    }
q3qa4bjr

q3qa4bjr2#

您也可以使用shutdown + awaitTermination来确保所有任务都已完成,并使用try-catch和AtomicBoolean来Assert“内部”没有引发AssertionErrors。

AtomicBoolean failed = new AtomicBoolean(false);
ExecutorService executorService = Executors.newFixedThreadPool(PARALLEL_POOL_SIZE);

// start tasks.. maybe in a loop to generate load..
executorService.execute(() -> {
  try {
    // Test something
    // ..
    // Validate
    assertThat(actual, equalTo(EXPECTED));
  } catch (AssertionError e) {
    failed.set(true);
    throw e;
  }
});

executorService.shutdown();
boolean terminatedInTime = executorService.awaitTermination(5, TimeUnit.SECONDS);
assertTrue(terminatedInTime);
assertFalse(failed.get());

相关问题