Junit 5 单元测试框架
Posted Master_hl
tags:
篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了Junit 5 单元测试框架相关的知识,希望对你有一定的参考价值。
目录
3.1 assertEquals/ assertNotEquals 断言是否匹配
3.2 assertTrue / assertFalse 断言结果的真假
3.3 assertNull / assertNotNull 断言结果是否为空
5.3 多参数数据来源 - 从第三方 csv 文件读取数据源
1. Junit 5 的依赖
<dependency>
<groupId>org.junit.jupiter</groupId>
<artifactId>junit-jupiter</artifactId>
<version>5.8.2</version>
<scope>test</scope>
</dependency>
<dependency>
<groupId>org.junit.platform</groupId>
<artifactId>junit-platform-suite</artifactId>
<version>1.8.2</version>
<scope>test</scope>
</dependency>
如果之前已经下载过 Junit 4 的相关依赖, 那么则需要先删除本地仓库的依赖, 再下载 Jnit5 的依赖.
2. Junit - 注解
2.1 @Test
该注解是用来加在测试的方法上面的, 表示该方法是测试方法, 并且当我们给方法加上 @Test 注解的时候, 当前方法就可以自己运行了, 不再需要 main 函数来调用. 而且当前类也可以自己运行了 , 运行当前类表示执行当前类里面所有加了 @Test 注解的方法.
不使用 @Test 注解之前, 测试方法需要的步骤 :
第一步 : 编写测试类, 编写测试方法.
第二步 : 编写运行测试类, 添加 main 方法, 实例化测试类, 调用相关测试方法.
使用 @Test 注解之后, 测试方法需要的步骤 :
由此对比, 使用 Junit 提供的注解来辅助自动化测试, 大大简化了代码的编写, 更加的方便了测试人员更好的进行测试.
并且, 在一个测试类中, 你想让哪些方法执行, 就在该方法上加 @Test 注解即可, 不想让它执行, 就去掉 @Test 注解即可, 非常方便.
执行结果 :
2.2 @BeforeEach
该注解是修饰方法的, 当一个测试方法加上 @BeforeEach 注解之后, 就表示当前方法需要在每个测试用例执行之前都执行一次. (注意加上 @BeforeEach 注解之后, 就不要加 @Test 注解了)
代码示例 :
public class JunitTest
@BeforeEach
void baseController()
System.out.println("before each");
@Test
void base1()
System.out.println("bbb");
@Test
void base2()
System.out.println("ccc");
执行结果 :
2.3 @BeforeAll
该注解是修饰方法的, 当一个测试方法加上 @BeforeAll 注解之后, 就表示当前方法需要在当前类下所有测试用例执行之前执行一次. 并且被该注解修饰的方法必须为静态方法.
在测试项目的时候, 可以把创建驱动对象单独写一个方法, 使用 @BeforeAll 注解修饰.
代码示例 :
public class JunitTest
@BeforeAll
static void baseController()
System.out.println("before all");
@Test
void base1()
System.out.println("bbb");
@Test
void base2()
System.out.println("ccc");
执行结果 :
2.4 @AfterEach
该注解是修饰方法的, 当一个测试方法加上 @AfterEach 注解之后, 就表示当前方法需要在每个测试用例执行之后都执行一次.
代码示例 :
public class JunitTest
@AfterEach
void baseController()
System.out.println("after each");
@Test
void base1()
System.out.println("bbb");
@Test
void base2()
System.out.println("ccc");
执行结果 :
2.5 @AfterAll
该注解是修饰方法的, 当一个测试方法加上 @AfterAll 注解之后, 就表示当前方法需要在当前类下所有测试用例执行之后执行一次. 并且被该注解修饰的方法必须为静态方法.
在测试项目的时候, 可以把释放驱动对象单独写一个方法, 使用 @AfterAll 注解修饰.
代码示例 :
public class JunitTest
@AfterAll
static void baseController()
System.out.println("after all");
@Test
void base1()
System.out.println("bbb");
@Test
void base2()
System.out.println("ccc");
执行结果 :
3. Junit - 断言
3.1 assertEquals/ assertNotEquals 断言是否匹配
例如我们获取一下百度首页中百度一下按钮上的文字 - 百度一下, 假如我们的预期结果是百度两下, 而打印的是百度一下, 此时就可以使用 assertEquals 来断言是否匹配. 该方法有两个参数, 第一个参数是预期结果, 第二个参数是实际结果.
代码示例 :
@Test
void baseAssert()
EdgeDriver driver = new EdgeDriver();
driver.get("https://www.baidu.com");
// 获取百度一下按钮上属性对应的值 - 百度一下
String text = driver.findElement(By.cssSelector("#su"))
.getAttribute("value");
System.out.println("预期结果: 百度两下, 实际结果 : " + text);
// 断言匹配
Assertions.assertEquals("百度两下", text); // false
// 断言不匹配
// Assertions.assertNotEquals("百度两下", text); // true
driver.quit();
执行结果 :
使用 assertNotEquals 断言不匹配, 程序执行结果 :
3.2 assertTrue / assertFalse 断言结果的真假
代码示例 :
@Test
void baseAssert1()
Assertions.assertTrue(1 == 1); // true
@Test
void bassAssert2()
Assertions.assertTrue(1 == 0); // false
@Test
void bassAssert3()
Assertions.assertFalse(1 == 1); // false
@Test
void bassAssert4()
Assertions.assertFalse(1 == 0); // true
执行结果 :
3.3 assertNull / assertNotNull 断言结果是否为空
代码示例 :
@Test
void baseAssert5()
String res = null;
Assertions.assertNull(res);
@Test
void baseAssert6()
String res = "hello";
Assertions.assertNull(res);
执行结果 :
4. Junit - 测试用例的执行顺序
先来看默认情况下, 多个测试用例的执行顺序.
代码示例 :
public class JunitTest
@Test // 2
void editLoginTest()
System.out.println("loginTest");
@Test // 1
void indexTest()
System.out.println("indexTest");
@Test // 3
void editTest()
System.out.println("editTest");
执行结果 :
从执行结果来看, 默认情况下, 多个测试用例的执行顺序是随机的 (可以调整顺序, 多运行几次) . 那么有时候我们一些登录的场景, 是需要按照顺序进行测试的, 比如说博客的登录系统, 我们要登录之后, 才能进入到博客列表页, 博客编辑页, 此时就需要针对多个测试用例指定执行顺序了.
使用 @Order 注解来指定多个测试用例的执行顺序 :
1. 先要使用 @TestMethodOrder 注解来说明当前类下所有的用例需要使用 Order 注解来进行排序, 当然也可以根据方法名排序, 但是常用的还是 Order 指定方法排序.
2. 然后通过 @Order 注解来指定测试用例的具体顺序.
3. @Test 注解不能删除.
代码示例 :
@TestMethodOrder(MethodOrderer.OrderAnnotation.class)
public class JunitTest
@Test
@Order(1)
void editLoginTest()
System.out.println("loginTest");
@Test
@Order(2)
void indexTest()
System.out.println("indexTest");
@Test
@Order(3)
void editTest()
System.out.println("editTest");
执行结果 :
5. Junit - 参数化
在登录场景中, 如果我们不使用参数化, 那么多个用户登录的时候, 我们的测试用例写起来就会非常麻烦, 如下 :
而我们期望的是尽可能的通过一个测试用例, 多组参数来模拟用户的登录行为.
1. 在使用参数化注解之前需要先使用 @ParamterizedTest 声明该方法为参数化方法.
2. 通过注解提供数据来源.
5.1 单参数数据来源
使用 @ValueSource 注解
@ValueSource(数据类型方法 = 参数1, 参数2, 参数3 .....)
@ParameterizedTest
@ValueSource(strings = "张三", "李四", "王五")
void singleParamTest(String name)
System.out.println(name);
执行结果 :
5.2 多参数数据来源 - 在注解里编写数据源
使用 @CsvSource 注解.
@CsvSource("第一组数据", "第二组数据", "第三组数据", ....) , 每一个双引号, 就是一组测试用例.
@ParameterizedTest
@CsvSource("张三, 123","李四, 123", "王五, 123")
void muchParamTest(String name, int age)
System.out.println("name: " + name + ", age : " + age);
执行结果 :
5.3 多参数数据来源 - 从第三方 csv 文件读取数据源
多参数场景下, 当在注解中的测试用例越来越多时, 代码的可读性就会非常差, 此时可以使用 @CsvFileSource 注解来从第三方 csv 文件中读取数据源.
@CsvFileSource(files = "文件路径")
@ParameterizedTest
@CsvFileSource(files = "D:\\\\aa\\\\abc.csv")
void csvFileParamTest(String name, int age)
System.out.println("name: " + name + ", age : " + age);
执行结果 :
5.4 多参数数据来源 - 通过动态方法来提供数据源
使用 @MethodSource 注解
@ParameterizedTest
@MethodSource("methodParams")
void dynamicMethodParamTest(String name, int age)
System.out.println("name : " + name + ",age : " + age);
static Stream<Arguments> methodParams() throws InterruptedException
// 构造动态参数
String[] array = new String[5];
for(int i = 0; i < array.length; ++i)
Thread.sleep(500);
array[i] = String.valueOf(System.currentTimeMillis());
return Stream.of(
Arguments.arguments(array[0], 21),
Arguments.arguments(array[1], 22),
Arguments.arguments(array[2], 23),
Arguments.arguments(array[3], 24),
Arguments.arguments(array[4], 25)
);
执行结果 :
此处指定的方法的返回类型 Arguments, 是因为一组数据的数据类型不同, 由 String 和 int 类型组合来的, 因此要使用组合类型 Arguments. 如果相同, 就可以写具体的类型.
【其他注意事项]
1. 当我们不指定数据源方法名时, 会自动的找跟用例方法名同名的静态方法.
2. 使用了参数化注解的方法不能再用 @Test 注解. (@Test 只能作用在非参数化的用例上)
6. JUnit - 测试套件
测试套件是用来指定当前包下哪些类中测试方法需要被执行, 如果没有测试套件, 我们很难去同时执行几个类下的测试用例.
准备工作 : 在 autoTest5 包下创建 aaa, bbb, ccc, 三个测试类, 分别给每个类加上测试方法, 以及前面创建好的 JunitTest 测试类.
6.1 指定类来运行用例
创建 runSuite 测试套件类, 添加@Suite注解, @SelectClasses 注解, 指定类运行类下的加了 @Test 注解, 或者参数化的测试用例.
@Suite
@SelectClasses(aaa.class,ccc.class)
public class runSuite
运行测试套件, 执行结果 :
6.2 指定包名来运行包下所有的用例
此时 autoTest5 包下有如下几个类 :
改写测试套件代码 :
@Suite
@SelectPackages("com.autoTest5")
public class runSuite
执行结果 :
autoTest5 包下明明有 4 个类, 为啥只运行了一个类中的测试用例呢 ?
如果使用包名来指定运行的范围, 那么该包下所有测试类的命名必须要以 Test/Tests 结尾 (T 必须要大写)
改类名 :
执行结果 :
本篇文章就到这里了, 谢谢观看~
junit-单元测试
一.JUnit简介
JUnit 是一个 Java编程语言的单元测试框架。JUnit 在测试驱动的开发方面有很重要的发展,是起源于 JUnit 的一个统称为 xUnit 的单元测试框架之一。
JUnit 是一个回归测试框架,被开发者用于实施对应用程序的单元测试,加快程序编制速度,同时提高编码的质量。JUnit 测试框架能够轻松完成以下任意两种结合:
- Eclipse 集成开发环境
- Ant 打包工具
- Maven 项目构建管理
二.JUnit使用
JUnit是程序员自己测试多个方法的单元测试框架 使用格式必须为 public void 方法名(){} 可以抛出异常
JUnit常用的注解 方法类型public static void
@BeforeClass 在测试类里所有用例运行之前,运行一次这个方法
@AfterClass 跟@BeforeClass对应,在测试类里所有用例运行之后,运行一次。用于处理一些测试后续工作,例如清理数据
JUnit可以和框架整合,更高效的测试 @RunWith
三.为什么使用JUnit测试
在程序里边,一个接口对应一个实现方法,而在接口中常常会定义相关的很多方法,所以在测试的时候,如果都在main方法里边进行测试,main方法就会显得臃肿,而且不便于以后其他人测试以及查看测试数据,用Junit Test测试的话,一个方法对应一个测试方法,简单明了,也方便别人查看测试方法以及测试数据。
四.总结
Junit是测试执行的开始阶段,即首先对每一个程序模块进行单元测试,以确保每个模块能正常工作。单元测试是程序员对自己的代码进行测试后,所以是大多是白盒测试。JUnit的最大作用就是可以方便的进行单个方法的测试。可与其他框架整合方便了JUnit的使用。
以上是关于Junit 5 单元测试框架的主要内容,如果未能解决你的问题,请参考以下文章