运行 来自 JUnit 基础的测试 class 在来自子 class 的测试之前

Run tests from JUnit base class before tests from subclass

对于某种测试,我有一个抽象的超级class和扩展这个超级class的子classes。在超级 class 中,我有一个名为 test0IfDirectoryCopied 的测试,它总是在测试子 class 时执行。它检查 subclass 中设置的资源是否设置正确。

虽然这很好,但不幸的是,这个 test0IfDirectoryCopied 只有在子 class 的所有测试都具有 运行 之后才会执行。由于它作为一种先决条件,如果它在任何子 class 测试之前执行将是最有帮助的。

附加信息:subclass 和 super class 都用 @FixMethodOrder(MethodSorters.NAME_ASCENDING) 注释,test0IfDirectoryCopied 是字典序中最小的条目

如果是前置条件你可以尝试用@before注解来注解前置条件。 但仍然:

您可以尝试 Junit.contrib 来做。 https://github.com/junit-team/junit.contrib/tree/master/assumes

您可以尝试定义一个测试套件并运行一个接一个

你可以尝试使用testng和@dependson注解

我找到了一个开箱即用的 JUnit 解决方案。我真正想要的是在我的整个测试 class 层次结构中的字典顺序测试执行顺序(尽管也可以定义其他策略,例如始终首先在基础 class 中执行测试)。我发现最简单的方法是实现我自己的 TestClassRunner:

public class LexicographicalTestOrderRunner extends BlockJUnit4ClassRunner {

    public LexicographicalTestOrderRunner(Class<?> klass) throws InitializationError {
        super(klass);
    }

    @Override
    protected List<FrameworkMethod> getChildren() {
        List<FrameworkMethod> children = super.getChildren();
        Collections.sort(children, new Comparator<FrameworkMethod>() {

            @Override
            public int compare(FrameworkMethod o1, FrameworkMethod o2) {
                return o1.getName().compareTo(o2.getName());
            }
        });

        return children;
    }
}

在我的基地class中指定这个跑步者就足够了,使用:

@RunWith(LexicographicalTestOrderRunner.class)

这样做的另一个好处是,我现在可以删除子 classes 中的所有 @FixMethodOrder 注释。

在不知道 test0IfDirectoryCopied 的细节的情况下,我认为实现一个可以添加到每个测试 class 的 rule 将是最好的解决方案。这也允许您摆脱测试 class 层次结构。

最新版本的 JUnit 有 Assume。基本上,如果假设失败,则忽略测试。

如果你把它放在 @Before 中但它失败了,测试 class 中的每个测试都将被忽略。

import static org.junit.Assume.*;
public class TestMySubClass extends TestSuperClass{

    @Before
    public void makesureDirectoryCopied(){

       assumeTrue( directoryCopied());
   }

   ...

其中 directoryCopied() 类似于您的 test0ifDirectoryCopied 除了它 returns truefalse 而不是抛出异常。

由于这是纯 JUnit,因此不需要额外的依赖项。

See Assume tutorial 了解更多信息