Vít*_*čka 7 java parameters junit unit-testing junit5
我想编写JUnit 5参数化测试,它将字符串数组(String[])作为参数:
@ParameterizedTest
@MethodSource("stringArrayProvider")
void parseFirstAndSecondInt(String[] args) {
Arguments arguments = new Arguments(args);
assertEquals(1, arguments.getFirst());
assertEquals(2, arguments.getSecond());
}
Run Code Online (Sandbox Code Playgroud)
我不确定,如何提供字符串数组的集合/流/迭代器.我没有成功尝试使用@MethodSource注释方法
static Stream<String[]> stringArrayProvider() {
return Stream.of(
new String[]{"1", "2"},
new String[]{"1", "2", "3"});
}
Run Code Online (Sandbox Code Playgroud)
但是我收到了这个例外:
org.junit.jupiter.params.converter.ArgumentConversionException:
No implicit conversion to convert object of type java.lang.String to type [Ljava.lang.String;
Run Code Online (Sandbox Code Playgroud)
有这种参数化测试的好设计/解决方案是什么?
Sor*_*ras 10
使用Arguments.of()工厂 fromorg.junit.jupiter.params.provider.Arguments来包装您的参数:
static Stream<Arguments> stringArrayProvider() {
return Stream.of(
Arguments.of((Object) new String[]{"1", "2"}),
Arguments.of((Object) new String[]{"1", "2", "3"})
);
}
Run Code Online (Sandbox Code Playgroud)
有关详细信息,请参阅http://junit.org/junit5/docs/current/user-guide/#writing-tests-parameterized-tests
我使用的第一个一般经验法则:
@ArgumentSource当多个测试类可以使用相同的生成测试用例时,使用(您的解决方案)
当相同生成的测试用例可以被多个测试方法(在同一个类中)使用时,使用@MethodSource(Sormuras解决方案)
否则尝试将测试用例的源保持为使用它们的方法尽可能本地
在最后一种情况下,我设想了两个简单的可能性:
你对固定数量的字符串感兴趣(所以不需要数组).您可以使用@CsvSource
这里有两个字符串的示例(也可能包括逗号).
@ParameterizedTest
@CsvSource({ "foo, 1", "bar, 2", "'baz, qux', 3" })
void testWithCsvSource(String first, String second) {
assertNotNull(first);
assertNotEquals(0, second);
}
Run Code Online (Sandbox Code Playgroud)
请注意,在这种情况下,如果各种元素不是真正的字符串,它们可能会被自动解析为正确的类型(例如,在您的问题中,您似乎想要整数)
你真的想要一个可变大小的字符串数组.在这种情况下,您可以使用@ValueSource然后将其内容转换为String []
直:
@ParameterizedTest
@ValueSource(strings = {"1, 2",
"1, 2, 3"})
void testWithArrayOfStrings(String arg) { // the single csv String parameter
String[] arrayParam = arg.split("\\s*,\\s*"); // is converted to an array of Strings
...
}
Run Code Online (Sandbox Code Playgroud)
或者使用@ConvertWith指示的Explicit Converter类:
@ParameterizedTest
@ValueSource(strings={"1, 2", "1, 2, 3"})
void testWithArrayOfStrings(@ConvertWith(CSVtoArray.class)String... arg)
{
...
}
public static class CSVtoArray extends SimpleArgumentConverter {
@Override
protected Object convert(Object source, Class<?> targetType) throws ArgumentConversionException {
String s = (String) source;
return s.split("\\s*,\\s*");
}
}
Run Code Online (Sandbox Code Playgroud)