【问题标题】:How to throw `InterruptedException` while junit testing my class?junit测试我的课程时如何抛出`InterruptedException`?
【发布时间】:2014-04-15 20:06:30
【问题描述】:

我正在尝试为使用 CountDownLatch 的类编写一些 junit,并且我正在使用 jmockit 库进行 junit 测试。

public class MappedData {

    private static final AtomicReference<Map<String, Map<Integer, String>>> mapped1 = new AtomicReference<Map<String, Map<Integer, String>>>();
    private static final AtomicReference<Map<String, Map<Integer, String>>> mapped2 = new AtomicReference<Map<String, Map<Integer, String>>>();
    private static final CountDownLatch firstSet = new CountDownLatch(1);

    public static Map<String, Map<Integer, String>> getMapped1Table() {
    try {
        firstSet.await();
    } catch (InterruptedException e) {
        throw new IllegalStateException(e);
    }
    return mapped1.get();
    }

    public static Map<String, Map<Integer, String>> getMapped2Table() {
    try {
        firstSet.await();
    } catch (InterruptedException e) {
        throw new IllegalStateException(e);
    }
    return mapped2.get();
    }
}

getMapped1TablegetMapped2Table 方法中确保最简单的方法是什么 - 我能够抛出InterruptedException 以便我也可以涵盖该场景。如果你看看这两种方法,我有一个我无法覆盖的 catch 块。

MappedData.getMapped1Table()

有什么方法可以确保我上面的两种方法都在抛出InterruptedException

更新:-

我想要做的是 - 当我进行 junit 测试时,如何让 firstSet.await() 抛出 InterruptedException。

【问题讨论】:

  • 你正在抛出一个IllegalStateException ...你会为此进行测试。
  • 我认为您要问的是如何让firstSet.await() 在测试时抛出InterruptedException。对吗?
  • @MikeB:是的,这就是我需要的……抱歉,我不够清楚……

标签: java junit jmockit interrupted-exception


【解决方案1】:

这是使用 JMockit 编写测试的最简单方法:

public class MappedDataTest
{
    @Test
    public void getMappedTableHandlesInterruptedException(
        @Mocked final CountDownLatch anyLatch) throws Exception
    {
        final InterruptedException interrupt = new InterruptedException();
        new NonStrictExpectations() {{ anyLatch.await(); result = interrupt; }};

        try {
            MappedData.getMapped1Table();
            fail();
        }
        catch (IllegalStateException e) {
            assertSame(interrupt, e.getCause());
        }
    }
}

【讨论】:

  • 谢谢。我们是否需要将anyLatch 实例值传递给getMappedTableHandlesInterruptedException 测试方法?
  • 不,它是由 JMockit 通过 JUnit 测试运行器间接传递的;这是自动且透明的。
  • 酷。谢谢您的帮助。我在 jmockit 上也有类似的问题here。看看你能不能帮帮我。谢谢。
【解决方案2】:

在单独的线程中调用该方法,然后中断该线程:

Thread t = new Thread(new Runnable(){
   public void run(){
      MappedData.getMappedTable();
    }
});

t.start();

t.interrupt();

【讨论】:

    【解决方案3】:

    您可以使用 MockitoEasyMock 等模拟库来完成此操作。您将需要一种注入模拟依赖项的方法。通常这是通过构造函数完成的,但由于您的字段是 static,您可能需要添加一个 setter。

    public static void setFirstSet(CountDownLatch latch)
    {
        firstSet = latch;
    }
    

    本示例的其余部分适用于 Mockito。

    在您的测试中,创建一个模拟 CountDownLatch

    CountDownLatch mockLatch = mock(CountDownLatch.class);
    

    然后存根方法抛出异常:

    when(mockLatch.await()).thenThrow(new InterruptedException());
    

    接下来注入模拟:

    MappedData.setFirstSet(mockLatch);
    

    最后调用被测方法:

    Map<String, Map<Integer, String>> result = MappedData.getMapped1Table();
    

    我从未使用过 jmockit,但通过快速的谷歌搜索表明这是这样做的方法:

    final CountDownLatch mockLatch = new CountDownLatch();
    new Expectations(mockLatch){
        {
            mockLatch.await();
            result = new InterruptedException();
        }
    };
    MappedData.setFirstSet(mockLatch);
    Map<String, Map<Integer, String>> result = MappedData.getMapped1Table();
    

    【讨论】:

    • 谢谢。我目前在我的代码库中使用 jmockit 库。如果可能的话,你能提供一个例子吗?对不起,我不够清楚。我也会编辑问题以添加它。
    • 我编辑了我认为如何使用 jmockit 进行的操作。我可以通过谷歌搜索找到,我肯定会建议将来先尝试一下。 abhinandanmk.blogspot.in/2012/06/…
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2016-11-09
    • 2016-06-20
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多