将参数传递给测试的JUnit @Rule

时间:2021-09-14 05:05:26

I'd like to create @Rule to be able to do something like this

我想创建@Rule来做这样的事情

@Test public void testValidationDefault(int i) throws Throwable {..}

Where i is parameter passed to the test by @Rule.

其中i是通过@Rule传递给测试的参数。

However I do get

然而我做得到

java.lang.Exception: Method testValidationDefault should have no parameters

is there any way to bypass it and set the i parameter in the @Rule?

有没有办法绕过它,在@Rule中设置i参数?

5 个解决方案

#1


8  

As IAdapter said you can't pass an argument using Rules, but you can do something similar.

正如IAdapter所说,您不能使用规则传递参数,但是您可以做一些类似的事情。

Implement a Rule that holds all your parameter values and evaluates the test once for every parameter value and offers the values through a method, so the test can pull them from the rule.

实现一个规则,该规则保存所有参数值,并对每个参数值进行一次评估,并通过一个方法提供这些值,以便测试能够从规则中提取它们。

Consider a Rule like this (pseudo code):

考虑这样的规则(伪代码):

public class ParameterRule extends MethodRule{
    private int parameterIndex = 0;
    private List<String> parameters;
    public ParameterRule(List<String> someParameters){ 
        parameters = someParameters;
    }

    public String getParameter(){
        return parameters.get(parameterIndex);
    }

    public Statement apply(Statement st, ...){
        return new Statement{
             public void evaluate(){
                 for (int i = 0; i < parameters.size(); i++){
                     int parameterIndex = i;
                     st.evaluate()
                 }      
             }
        }
    }
}

You should be able to use this in a Test like this:

你应该能够在这样的测试中使用这个:

 public classs SomeTest{
     @Rule ParameterRule rule = new ParameterRule(ArrayList<String>("a","b","c"));

     public void someTest(){
         String s = rule.getParameter()

         // do some test based on s
     }
 }

#2


8  

I use @Parameters and @RunWith(value = Parameterized.class) for passing values to tests. An example can be found here.

我使用@Parameters和@RunWith(value = parameter .class)来将值传递给测试。这里可以找到一个例子。

I did not know about the @Rule annotation, but after reading this post, I think it serves another purpose than passing parameters to the tests:

我不知道@Rule注释,但是读了这篇文章后,我认为它除了向测试传递参数之外还有另外一个目的:

If in your test class, you create a field pointing to an object implementing the MethodRule interface, and you mark this to be processed as a rule, by adding the @Rule implementation, then JUnit will call back on your instance for every test it will run, allowing you to add additional behavior around your test execution.

如果在测试类中,您创建一个字段指向一个对象实现MethodRule接口,处理你马克这个规则,通过添加@Rule实现,那么JUnit将回电话在您的实例为每个测试运行,允许您添加额外的行为在你的测试执行。

I hope this helps.

我希望这可以帮助。

#3


2  

recently i started zohhak project. it lets you write tests with parameters (but it's a runner, not a rule):

最近我开始了zohhak项目。它允许您使用参数编写测试(但它是一个运行程序,而不是一个规则):

@TestWith({
   "25 USD, 7",
   "38 GBP, 2",
   "null,   0"
})
public void testMethod(Money money, int anotherParameter) {
   ...
}

#4


0  

It should be noted that it is no longer true that you can't pass parameters directly to a test method. It can now be done using Theories and @DataPoints/@DataPoint.

应该注意的是,您不能直接将参数传递给测试方法已不再是事实。现在可以使用理论和@DataPoints/@DataPoint来完成。

For example:

例如:

@RunWith(Theories.class)
public class TestDataPoints {

    @DataPoints
    public static int [] data() {
        return new int [] {2, 3, 5, 7};
    }

    public int add(int a, int b) {
        return a + b;
    }

    @Theory
    public void testTheory(int a, int b) {
        System.out.println(String.format("a=%d, b=%d", a, b));
        assertEquals(a+b, add(a, b));
    }
}

Output:

输出:

a=2, b=2
a=2, b=3
a=2, b=5
a=2, b=7
a=3, b=2
a=3, b=3
a=3, b=5
a=3, b=7
a=5, b=2
a=5, b=3
a=5, b=5
a=5, b=7
a=7, b=2
a=7, b=3
a=7, b=5
a=7, b=7

With the test passing.

测试通过。

#5


-2  

it can't be done, you can't pass parameters to test method even using @Rule.

这是不可能的,即使使用@Rule你也不能将参数传递给测试方法。

#1


8  

As IAdapter said you can't pass an argument using Rules, but you can do something similar.

正如IAdapter所说,您不能使用规则传递参数,但是您可以做一些类似的事情。

Implement a Rule that holds all your parameter values and evaluates the test once for every parameter value and offers the values through a method, so the test can pull them from the rule.

实现一个规则,该规则保存所有参数值,并对每个参数值进行一次评估,并通过一个方法提供这些值,以便测试能够从规则中提取它们。

Consider a Rule like this (pseudo code):

考虑这样的规则(伪代码):

public class ParameterRule extends MethodRule{
    private int parameterIndex = 0;
    private List<String> parameters;
    public ParameterRule(List<String> someParameters){ 
        parameters = someParameters;
    }

    public String getParameter(){
        return parameters.get(parameterIndex);
    }

    public Statement apply(Statement st, ...){
        return new Statement{
             public void evaluate(){
                 for (int i = 0; i < parameters.size(); i++){
                     int parameterIndex = i;
                     st.evaluate()
                 }      
             }
        }
    }
}

You should be able to use this in a Test like this:

你应该能够在这样的测试中使用这个:

 public classs SomeTest{
     @Rule ParameterRule rule = new ParameterRule(ArrayList<String>("a","b","c"));

     public void someTest(){
         String s = rule.getParameter()

         // do some test based on s
     }
 }

#2


8  

I use @Parameters and @RunWith(value = Parameterized.class) for passing values to tests. An example can be found here.

我使用@Parameters和@RunWith(value = parameter .class)来将值传递给测试。这里可以找到一个例子。

I did not know about the @Rule annotation, but after reading this post, I think it serves another purpose than passing parameters to the tests:

我不知道@Rule注释,但是读了这篇文章后,我认为它除了向测试传递参数之外还有另外一个目的:

If in your test class, you create a field pointing to an object implementing the MethodRule interface, and you mark this to be processed as a rule, by adding the @Rule implementation, then JUnit will call back on your instance for every test it will run, allowing you to add additional behavior around your test execution.

如果在测试类中,您创建一个字段指向一个对象实现MethodRule接口,处理你马克这个规则,通过添加@Rule实现,那么JUnit将回电话在您的实例为每个测试运行,允许您添加额外的行为在你的测试执行。

I hope this helps.

我希望这可以帮助。

#3


2  

recently i started zohhak project. it lets you write tests with parameters (but it's a runner, not a rule):

最近我开始了zohhak项目。它允许您使用参数编写测试(但它是一个运行程序,而不是一个规则):

@TestWith({
   "25 USD, 7",
   "38 GBP, 2",
   "null,   0"
})
public void testMethod(Money money, int anotherParameter) {
   ...
}

#4


0  

It should be noted that it is no longer true that you can't pass parameters directly to a test method. It can now be done using Theories and @DataPoints/@DataPoint.

应该注意的是,您不能直接将参数传递给测试方法已不再是事实。现在可以使用理论和@DataPoints/@DataPoint来完成。

For example:

例如:

@RunWith(Theories.class)
public class TestDataPoints {

    @DataPoints
    public static int [] data() {
        return new int [] {2, 3, 5, 7};
    }

    public int add(int a, int b) {
        return a + b;
    }

    @Theory
    public void testTheory(int a, int b) {
        System.out.println(String.format("a=%d, b=%d", a, b));
        assertEquals(a+b, add(a, b));
    }
}

Output:

输出:

a=2, b=2
a=2, b=3
a=2, b=5
a=2, b=7
a=3, b=2
a=3, b=3
a=3, b=5
a=3, b=7
a=5, b=2
a=5, b=3
a=5, b=5
a=5, b=7
a=7, b=2
a=7, b=3
a=7, b=5
a=7, b=7

With the test passing.

测试通过。

#5


-2  

it can't be done, you can't pass parameters to test method even using @Rule.

这是不可能的,即使使用@Rule你也不能将参数传递给测试方法。