【问题标题】:Run tests from JUnit base class before tests from subclass在来自子类的测试之前从 JUnit 基类运行测试
【发布时间】:2015-06-28 10:07:43
【问题描述】:

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

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

附加信息:子类和超类都用@FixMethodOrder(MethodSorters.NAME_ASCENDING)注解,test0IfDirectoryCopied是字典序上最小的条目

【问题讨论】:

    标签: java unit-testing inheritance junit


    【解决方案1】:

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

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

    import static org.junit.Assume.*;
    public class TestMySubClass extends TestSuperClass{
    
        @Before
        public void makesureDirectoryCopied(){
    
           assumeTrue( directoryCopied());
       }
    
       ...
    

    directoryCopied() 与您的 test0ifDirectoryCopied 类似,只是它返回 truefalse 而不是引发异常。

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

    See Assume tutorial 了解更多信息

    【讨论】:

    • 优秀的答案。谢谢!
    【解决方案2】:

    如果它是前提条件,您可以尝试使用 @before 注释来注释前提条件。 但还是:

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

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

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

    【讨论】:

    • @before 在每个测试方法之前执行,这不是我想要的。 @beforeClass 不起作用,因为那时我的资源尚未设置。此外,我希望将test0IfDirectoryCopied 作为正常测试执行,而上述两种方法都没有。我看不到如何使用 TestSuites 来获得所需的行为。我不想向 testng 添加依赖项。 Junit.contrib 的@Assumes 做我想做的事。但是,我也不想向 Junit.contrib 添加依赖项。
    • 好吧,当使用 testng 时,我可以在子类中声明一个默认构造函数,以便父类的测试在我的子类之前运行。它也适用于junit吗?
    【解决方案3】:

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

    【讨论】:

      【解决方案4】:

      我找到了一个开箱即用的 JUnit 解决方案。我真正想要的是整个测试类层次结构中的字典测试执行顺序(尽管也可以定义其他策略,例如始终首先在基类中执行测试)。我发现实现这一点的最简单方法是实现我自己的 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;
          }
      }
      

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

      @RunWith(LexicographicalTestOrderRunner.class)
      

      作为额外的好处,我现在可以删除子类中的所有 @FixMethodOrder 注释。

      【讨论】:

        猜你喜欢
        • 2011-01-30
        • 2023-03-25
        • 1970-01-01
        • 2010-11-14
        • 2011-01-09
        • 2017-08-30
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        相关资源
        最近更新 更多