Java优秀测试框架TestNG详解
作者:再来一块红烧肉
我们为什么需要TestNG?
Java有好几个测试框架,JUnit是比较常见的一个,Spring系列默认的测试框架就是JUnit。TestNG也是Java的一个测试框架,与JUnit功能类似, 但支持更多的注解与功能。
我们常使用JUnit做单元测试,而在做自动化测试时,更偏向于选择TestNG。
TestNG搭建
Maven工程中,添加TestNG依赖包即可,可自行选择版本:
<dependency> <groupId>org.testng</groupId> <artifactId>testng</artifactId> <version>7.1.0</version> <scope>test</scope> </dependency>
TestNG注解及功能
TestNG的注解与JUnit类似,但会更丰富,更细致:
注解 | 描述 |
---|---|
@Test | 标记一个类里所有的public void方法,或某个方法,作为测试案例。 |
@BeforeSuite | 对于套件测试,在此套件中的所有测试执行之前运行,仅运行一次。 |
@AfterSuite | 对于套件测试,在此套件中的所有测试执行之后运行,仅运行一次。 |
@BeforeClass | 在调用当前类之前运行,只运行一次。 |
@AfterClass | 在调用当前类之后运行,只运行一次。 |
@BeforeTest | 对于套件测试,在属于标签内的所有类的测试方法执行之前运行。 |
@AfterTest | 对于套件测试,在属于标签内的所有类的测试方法都已执行完之后运行。 |
@BeforeGroups | 在调用属于该组的第一个测试方法之前运行。 |
@AfterGroups | 在调用属于该组的最后一个测试方法执行之后运行 。 |
@BeforeMethod | 注解的方法将每个测试方法之前运行。 |
@AfterMethod | 在每个测试方法执行之前都会运行。 |
@DataProvider | 标志着一个方法,提供数据的一个测试方法。注解的方法必须返回一个Object[] [],其中每个对象[]的测试方法的参数列表中可以分配。该@Test 方法,希望从这个DataProvider的接收数据,需要使用一个dataProvider名称等于这个注解的名字。 |
@Factory | 作为一个工厂,返回TestNG的测试类的对象将被用于标记的方法。该方法必须返回Object[]。 |
@Listeners | 定义一个测试类的监听器。 |
@Parameters | 用于将参数传递给@Test方法。 |
TestNG配置文件
对比JUnit,TestNG最显眼的区别就是多了一个配置文件。
有了这个配置文件的存在,可以更方便的管理测试案例的执行。
1.新增配置文件
在项目根目录下,新增testng.xml格式的配置文件,文件名任意,配置文件可以有多个。
maven工程在pom文件中,指定配置文件路径后,可以直接运行配置文件:
<plugin> <groupId>org.apache.maven.plugins</groupId> <artifactId>maven-surefire-plugin</artifactId> <version>3.0.0-M4</version> <configuration> <suiteXmlFiles> <suiteXmlFile>./testng.xml</suiteXmlFile> </suiteXmlFiles> </configuration> </plugin>
TestNG配置的内容并不复杂,这里的配置并不是TestNG启动的依赖,而是对测试案例的执行方式进行划分。
2.配置测试套件(suit)
一个配置文件,有且只能有一个测试套件。suit标签的常见属性如下,其中name为强制填写的,会展示在最终的测试报告中。
属性 | 描述 |
---|---|
name | 套件的名称,这是一个强制属性 |
verbose | 运行的级别或详细程度,级别为0-10,其中10最详细 |
parallel | TestNG是否运行不同的线程来运行这个套件,默认为none,其他级别为methods、tests、classes、instances |
thread-count | 如果启用并行模式(忽略其他方式),则为使用的线程数 |
annotations | 在测试中使用的注释类型 |
time-out | 在本测试中的所有测试方法上使用的默认超时 |
preserve-order | 用于配置测试案例是否按顺序执行 |
3.配置测试案例
按照groups组进行划分(使用了@Test (groups={“group1”})进行注解的),include标签标注的组名会被执行,被exclude标注的组则不会被执行:
<groups> <run> <include name = "includedGroupName" /> <exclude name = "excludedGroupName" /> </run> </groups>
按照包、类、方法三个层级划分:
包:
<packages> <package name = "com.hhm.demo1.*" /> <package name = "com.hhm.demo2.*" /> </packages>
类:
<classes> <class name="com.hhm.demo1.DemoTest1"/> <class name="com.hhm.demo1.DemoTest2"/> </classes>
方法:
<classes> <class name="com.hhm.demo1.DemoTest1"> <methods> <include name="testMethodName"></include> </methods> </class> </classes>
完整配置示例:
<!DOCTYPE suite SYSTEM "http://testng.org/testng-1.0.dtd" > <suite name="First suite" verbose="1" > <test name="MyTest" parallel="classes" thread-count="4"> <packages> <package name="com.hhm.demo1.*"></package> <package name="com.hhm.demo2.*"></package> </packages> </test> </suite>
配置完成后,可以直接运行配置文件,以执行测试案例。也可以通过maven-Lifecycle的test命令执行。
TestNG测试
1.异常测试
预期异常测试通过在@Test注解后加入预期的Exception来进行添加,示例如下:
@Test(expectedExceptions = ArithmeticException.class) public void divisionWithException() { int i = 1 / 0; System.out.println("After division the value of i is :"+ i); }
2.忽略测试
有时候我们写的用例没准备好,或者该次测试不想运行此用例,那么删掉显然不明智,那么就可以通过注解@Test(enabled = false)
来将其忽略掉,此用例就不会运行了,如下范例:
public class DemoTest1{ @Test(enabled=false) public void TestNgLearn1() { System.out.println("this is TestNG test case1"); } @Test public void TestNgLearn2() { System.out.println("this is TestNG test case2"); } }
3.超时测试
“超时”表示如果单元测试花费的时间超过指定的毫秒数,那么TestNG将会中止它并将其标记为失败。此项常用于性能测试。如下为一个范例:
public class DemoTest2{ @Test(timeOut = 5000) // time in mulliseconds public void testThisShouldPass() throws InterruptedException { Thread.sleep(4000); } @Test(timeOut = 1000) public void testThisShouldFail() { while (true){ // do nothing } } }
4.参数化测试
4.1 使用XML配置文件提供
代码如下:
public class DemoTest2 { @Parameters({"param1", "param2"}) public void TestNgLearn1(String param1, int param2) { System.out.println("this is TestNG test case1, and param1 is:"+param1+"; param2 is:"+param2); Assert.assertFalse(false); } }
XML配置如下:
<!DOCTYPE suite SYSTEM "http://testng.org/testng-1.0.dtd" > <suite name="First suite" verbose="1" > <test name="MyTest"> <parameter name="param1" value="1011111" /> <parameter name="param2" value="10" /> <classes> <class name="com.hhm.demo1.DemoTest2"/> </classes> </test> </suite>
4.2 使用@DataProvider传递参数
此处需要注意,传参的类型必须要一致,且带有@DataProvider注解的函数返回的必然是Object[][],此处需要注意。当提供多组数据时,测试案例则会执行相应次数。
public class DemoTest2 { @DataProvider(name = "provideNumbers") public Object[][] provideData() { return new Object[][] { { 10, 20 }, { 100, 110 }, { 200, 210 } }; } @Test(dataProvider = "provideNumbers") public void TestNgLearn1(int param1, int param2) { System.out.println("this is TestNG test case1, and param1 is:"+param1+"; param2 is:"+param2); Assert.assertFalse(false); } }
5.依赖测试
有时候,我们需要按顺序来调用测试用例,那么测试用例之间就存在依赖关系。 TestNG支持测试用例之间的依赖,使用dependOnMethods和dependsOnGroups来实现依赖测试。如下案例,TestNgLearn1()案例失败时,TestNgLearn2()案例则不会执行:
public class DemoTest1 { public void TestNgLearn1() { System.out.println("this is TestNG test case1"); Assert.assertFalse(true); } @Test(dependsOnMethods= {"TestNgLearn1"}) public void TestNgLearn2() { System.out.println("this is TestNG test case2"); } }
TestNG测试报告
使用maven执行完测试用例后,会在 工程根目录\target\surefire-reports 目录下,生成测试报告文件,点击index.html文件则可以在浏览器中查看。
这里的报告比较简单,不够美观。我们可以结合Allure插件,生成更美观的测试报告。
总结
本篇文章就到这里了,希望能够给你带来帮助,也希望您能够多多关注脚本之家的更多内容!