如何根据条件禁用TestNG测试

时间:2010-10-15 20:13:50

标签: java eclipse annotations testng java-5

目前是否有办法根据条件禁用TestNG测试

我知道您当前可以在TestNG中禁用测试:

@Test(enabled=false, group={"blah"})
public void testCurrency(){
...
}

我想根据条件禁用相同的测试,但不知道如何。像这样的东西:

@Test(enabled={isUk() ? false : true), group={"blah"})
public void testCurrency(){
...
}

任何人都知道这是否可能。

7 个答案:

答案 0 :(得分:34)

更简单的选择是在检查条件的方法上使用@BeforeMethod注释。如果您想跳过测试,那么只需抛出SkipException。像这样:

@BeforeMethod
protected void checkEnvironment() {
  if (!resourceAvailable) {
    throw new SkipException("Skipping tests because resource was not available.");
  }
}

答案 1 :(得分:14)

您有两种选择:

您的注释转换器将测试条件,然后覆盖@Test注释以在不满足条件时添加属性“enabled = false”。

答案 2 :(得分:8)

我知道有两种方法可以控制TestNG中的“禁用”测试。

非常重要的区别是,SkipException将突破所有后续测试,同时实施IAnnotationTransformer根据您指定的条件使用Reflection来取消单个测试。我将解释SkipException和IAnnotationTransfomer。

跳过例外

import org.testng.*;
import org.testng.annotations.*;

public class TestSuite
{
    // You set this however you like.
    boolean myCondition;

    // Execute before each test is run
    @BeforeMethod
    public void before(Method methodName){
        // check condition, note once you condition is met the rest of the tests will be skipped as well
        if(myCondition)
            throw new SkipException();
    }

    @Test(priority = 1)
    public void test1(){}

    @Test(priority = 2)
    public void test2(){}

    @Test(priority = 3)
    public void test3(){}
}

IAnnotationTransformer示例

有点复杂,但背后的想法是一个被称为反射的概念。

Wiki - http://en.wikipedia.org/wiki/Reflection_(computer_programming)

首先实现IAnnotation接口,将其保存在* .java文件中。

import java.lang.reflect.Constructor;
import java.lang.reflect.Method;
import org.testng.IAnnotationTransformer;
import org.testng.annotations.ITestAnnotation;

public class Transformer implements IAnnotationTransformer {

// Do not worry about calling this method as testNG calls it behind the scenes before EVERY method (or test).
// It will disable single tests, not the entire suite like SkipException
public void transform(ITestAnnotation annotation, Class testClass, Constructor testConstructor, Method testMethod){

    // If we have chose not to run this test then disable it.
    if (disableMe()){
        annotation.setEnabled(false);
    }
}

// logic YOU control
private boolean disableMe()){
}

然后在你的测试套件java文件中,在@BeforeClass函数中执行以下操作

import org.testng.*;
import org.testng.annotations.*;

/* Execute before the tests run. */    
@BeforeClass
public void before(){

    TestNG testNG = new TestNG();
    testNG.setAnnotationTransformer(new Transformer());
}

@Test(priority = 1)
public void test1(){}

@Test(priority = 2)
public void test2(){}

@Test(priority = 3)
public void test3(){}

最后一步是确保在build.xml文件中添加侦听器。 我最终看起来像这样,这只是build.xml中的一行:

<testng classpath="${test.classpath}:${build.dir}" outputdir="${report.dir}" 
    haltonfailure="false" useDefaultListeners="true"
    listeners="org.uncommons.reportng.HTMLReporter,org.uncommons.reportng.JUnitXMLReporter,Transformer" 
    classpathref="reportnglibs"></testng>

答案 3 :(得分:2)

第三选项也可以是假设 Assumptions for TestNG-当假设失败时,将指示TestNG忽略测试用例,因此将不执行它。

  • 使用@Assumption批注
  • 使用Assumes.assumeThat(...)使用AssumptionListener 方法

您可以使用以下示例:example

答案 4 :(得分:1)

我更喜欢这种基于注释的方式,用于基于环境设置禁用/跳过某些测试。易于维护,不需要任何特殊的编码技术。

  • 使用IInvokedMethodListener接口
  • 创建自定义注释,例如:@SkipInHeadlessMode
  • 引发SkipException
#if PY_MAJOR_VERSION==2

       void initpymqe(void) {
       …
#else

检查详细信息: https://www.lenar.io/skip-testng-tests-based-condition-using-iinvokedmethodlistener/

答案 5 :(得分:0)

SkipException:如果类中只有一个@Test方法,这很有用。像数据驱动框架一样,我只有一个Test方法,该方法需要根据某些条件执行或跳过。因此,我将检查条件的逻辑放在@Test方法中,并获得了所需的结果。 它帮助我获得具有测试用例结果(通过/失败)以及特定跳过的扩展报告。

答案 6 :(得分:-1)

在使用SkipException注释的方法中抛出@BeforeMethod对我来说不起作用,因为它跳过了我的测试套件的所有剩余测试而不关心是否为这些测试引发了SkipException测试

我没有彻底调查,但我找到了另一种方法:使用dependsOnMethods注释上的@Test属性:

import org.testng.SkipException;
import org.testng.annotations.Test;

public class MyTest {

  private boolean conditionX = true;
  private boolean conditionY = false;

  @Test
  public void isConditionX(){
    if(!conditionX){
      throw new SkipException("skipped because of X is false");
    }
  }

  @Test
  public void isConditionY(){
    if(!conditionY){
      throw new SkipException("skipped because of Y is false");
    }
  }

  @Test(dependsOnMethods="isConditionX")
  public void test1(){

  }

  @Test(dependsOnMethods="isConditionY")
  public void test2(){

  }
}