目录
一. 认识 Junit
二. Junit 的常用注解
1. @Test
2. @Disabled
3. @BeforeAll
4. @AfterAll
5. @BeforeEach
6. @AfterEach
7. 执行测试
三. 参数化
1. 引入依赖
2. 单参数
3. 多参数
3.1 通过CSV实现
3.2 通过方法实现
4. 测试用例的执行顺序
四. 断言
五. 测试套件
一. 认识 Junit
Junit 是针对 Java 的一个单元测试框架,在上一篇文章中也介绍了 selenium ,它是自动化测试框架。
他们两者之间可以这样来认识:selenium是用来写自动化测试用例的技术,而Junit是用来管理已经编写好的测试用例的技术;
二. Junit 的常用注解
首先需要引入依赖:
<!-- https://mvnrepository.com/artifact/org.junit.jupiter/junit-jupiter-api -->
<dependency>
<groupId>org.junit.jupiter</groupId>
<artifactId>junit-jupiter-api</artifactId>
<version>5.9.1</version>
</dependency>
1. @Test
@Test 注解用于方法上面,表示当前的方法是一个测试用例,通过@Test注释后的方法,不需要在main中,也可以直接运行。
@Test
void Test01(){ // 此处要么不写,要么写 public,写别的就不被当成测试用例了
System.out.println("这是 junit 里面的 test01");
}
2. @Disabled
当使用 @Disabled 注释时,表示当前的测试用例不执行。
3. @BeforeAll
@BeforeAll 表示当前的测试用例在所有测试用例开始执行之前先执行。
需要注意的是:@BeforeAll 注释的方法必须是静态的,只会执行一次。
联系到前面所学的自动化测试,我们通常可以将 创建驱动,打开网页的操作 放在此注解下。
4. @AfterAll
@AfterAll 表示当前的测试用例在所有测试用例执行完之后再开始执行。
需要注意的是:@AfterAll 注释的方法必须是静态的,只会执行一次。
联系到前面所学的自动化测试,我们通常可以将 关闭浏览器 放在此注解下。
5. @BeforeEach
@BeforeEach 表示执行每一个测试用例之前,都会先执行一遍当前的方法。
6. @AfterEach
@AfterEach 表示执行每一个测试用例之后,都会先执行一遍当前的方法。
7. 执行测试
根据上述的注解,可以观察以下代码的执行结果。
public class JunitTest {
@Test
void Test01(){ // 此处要么不写,要么写 public,写别的就不被当成测试用例了
System.out.println("这是 junit 里面的 test01");
}
@Disabled
//类似于 @ignore 但是 @ignore 不属于junit,表示不执行
void Test02(){
System.out.println("不执行");
}
@BeforeAll // 注意static修饰,在所有测试用例之前先执行
static void Test03(){
System.out.println("beforeAll");
}
@AfterAll // 注意static修饰,在所有测试用例之后再执行
static void Test04(){
System.out.println("afterAll");
}
@BeforeEach
void Test05(){
System.out.println("执行 BeforeEach");
}
@AfterEach
void Test06(){
System.out.println("执行 AfterEach");
}
@Test
void Test07(){ // 此处要么不写,要么写 public,写别的就不被当成测试用例了
System.out.println("这是 junit 里面的 test07");
}
}
三. 参数化
当执行测试用例的时候,有时候是需要进行参数化的。
主要使用注解:@ParameterizedTest 表示参数注册,也表示测试用例
注意:@ParameterizedTest 和 @Test 不能同时使用
1. 引入依赖
<!-- https://mvnrepository.com/artifact/org.junit.jupiter/junit-jupiter-params -->
<dependency>
<groupId>org.junit.jupiter</groupId>
<artifactId>junit-jupiter-params</artifactId>
<version>5.9.1</version>
</dependency>
2. 单参数
单参数,指的是传递的参数类型是单种形式的。
主要使用注解:@ValueSource( 参数类型 )
参数类型可以有多种形式:
@ParameterizedTest // 参数注册
@ValueSource(ints = {1,2,3}) // 单参数:传递数据的类型是单种形式的
void Test08(int num){
System.out.println(num); // 参数有三个,会执行三次
}
3. 多参数
多参数,指的是传递的参数可以是多种类型的。
3.1 通过CSV实现
首先可以使用 @CsvSource("参数") 可以将参数直接传入,可以传入多种类型的参数;
例如:@CsvSource(" 1,2,'你好' ");
@ParameterizedTest
@CsvSource({"1,2,'你好呀',''"}) // 此处可以将数据直接放入
void Test01(int x,int y,String z,String q){
System.out.println(x); // 1
System.out.println(y); // 2
System.out.println(z); // 你好呀
System.out.println(q); // 空字符串
System.out.println("============");
}
也可以使用 @CsvFileSource(resource = "csv文件")
这个方法一般会在resources路径下,创建一个 csv文件 ,将想要传入的参数写入 csv文件中即可 。每一次运行就对应 csv文件中的一行。
@ParameterizedTest
@CsvFileSource(resources = "test02.csv")
void Test02(int num,String name){
System.out.println(num + ":" + name);
}
3.2 通过方法实现
通过 @MethodSource("方法名") 注解来实现,要构造方法名对应的方法 ,在对应的方法中,返回相应类型的参数。
public static Stream<Arguments> Generator() {
return Stream.of(Arguments.arguments(1,"张三"),
Arguments.arguments(2,"李四"),
Arguments.arguments(3,"王五")
);
}
@ParameterizedTest
@MethodSource("Generator")
void Test11(int num,String name){
System.out.println(num + ":" + name);
}
public static Stream<Arguments> Generate() {
return Stream.of(Arguments.arguments("1,张三","2,李四","3,王五"));
}
@ParameterizedTest
@MethodSource("Generate")
void Test03(String numName1,String numName2,String numName3){
System.out.println(numName1+" "+numName2+" "+numName3);
}
4. 测试用例的执行顺序
当需要对测试用例进行顺序执行的时候,就需要到注解
@TestMethodOrder(MethodOrderer.OrderAnnotation.class)
不需要顺序执行就默认为:
@TestMethodOrder(MethodOrderer.Random.class)
应该注意的是:无顺序,并不是默认从上到下执行,此处的执行顺序是根据 Junit 的运行机制来的。
这两个注解是用在类上的;
然后还需要再对应的方法上加上注解 @Order() 来进行想要的执行顺序规定
@TestMethodOrder(MethodOrderer.OrderAnnotation.class) // 按顺序
//@TestMethodOrder(MethodOrderer.Random.class) // 无顺序( 不一定是从上到下,是根据junit的运行机制来的 )
public class JunitTest02 {
@Order(2)
@Test
void Test01(){
System.out.println("111");
}
@Order(1)
@Test
void Test02(){
System.out.println("222");
}
@Order(4)
@Test
void Test03(){
System.out.println("333");
}
@Order(3)
@Test
void Test04(){
System.out.println("444");
}
}
当不需要顺序执行的时候,可以看出也并不是从上到下执行的,验证了上述的内容:
四. 断言
写自动化测试,结果要么是成功的,要么是失败的,不存在成功一半的情况。
那么就需要使用到断言:assert,断言预期结果和真实结果是否一致。
主要用到的方法就是:
断言相等:Assertions.assertEquals(预期结果,实际值) -- 两者相等,测试通过
断言不相等:Assertions.assertNotEquals(预期结果,实际值) -- 两者不相等,测试通过
断言为空:Assertions.assertNull(参数) -- 参数为空,测试通过
断言不为空:Assertions.assertNotNull(参数) -- 参数不为空,测试通过
以下代码都可以测试通过:
public class JunitTest03 {
@ParameterizedTest
@ValueSource(ints = {1})
void Test01(int num){
System.out.println(num);
Assertions.assertEquals(1,num); // 等于 1 测试通过
Assertions.assertNotEquals(2,num); // 不等于 2 测试通过
String str = "null";
String str2 = null;
Assertions.assertNull(str2); // 值为空,则测试通过
Assertions.assertNotNull(str); // 值不为空,测试通过
}
}
五. 测试套件
测试套件,主要就是用于把想执行的测试用例执行起来。
使用注解:@Suite,作用于类上;
需要引入依赖
<!-- 测试套件-->
<!-- https://mvnrepository.com/artifact/org.junit.platform/junit-platform-suite -->
<dependency>
<groupId>org.junit.platform</groupId>
<artifactId>junit-platform-suite</artifactId>
<version>1.9.1</version>
</dependency>
<!-- https://mvnrepository.com/artifact/org.junit.jupiter/junit-jupiter-engine -->
<dependency>
<groupId>org.junit.jupiter</groupId>
<artifactId>junit-jupiter-engine</artifactId>
<version>5.9.1</version>
<scope>test</scope>
</dependency>
1. @SelectClasses({指定类}) 通过参数中指定对应的类,然后对类中的测试用例进行执行,此处又有后顺序;作用于类上
2. @SelectPackages({"指定包"}) 通过参数中指定对应的包,然后对包中的测试用例进行执行,但是扫描的包不可以和当前的类在同一个包下面;作用于类上