在自动化测试的知识体系中,最推荐使用API的自动化测试,在基于API的自动化测试中,也是提升测试效率最有效的
手段之一。这是因为,在UI的自动化测试中,它是无法满足互联网公司的快速交付的节奏,UI自动化测试不管是否承认于是
否,它在执行上面都是存在缺陷的,也就是它的执行耗时是很长的,虽然可以引入显式等待以及隐式等待的技术,但是还是
无法来解决这个问题。在谈到API的自动化测试知识体系中,我们需要掌握HTTP的协议,也就是应用层的协议,需要系统性
的了解常用的请求方法,请求状态码,请求头以及响应头信息,和服务之间的通信模式。在API的自动化测试没模式中,其
实就是请求/响应的模式,为什么这样说了?我们先不回答这个问题,我们就拿目前比较主流的微服务架构而言,它是基于
轻量级的REST API的通信模式来进行交互,那么在服务进行交互的时候,通常有同步通信和异步通信,不管是同步模式还
是异步模式,它都是基于应用层的协议,所以我们首先需要清楚的知识一个完整的HTTP的请求流程,具体如下:
在如上的模式中,我们可以看到,在客户端与服务端之间的交互中,涉及到的主要步骤为:
HTTP是基于应用层的协议,它不需要关注底层网络传属层协议的事,但是客户端与服务交互首先需要建立TCP的连接
建立TCP的连接后,客户端向服务端发送Request的请求,当然这中间可能涉及到同步通信,也可能是异步通信
服务端接收到客户端的请求信息后,服务端响应回复客户端,也就是Response的过程。
最后,客户端与服务端之间的交互完成后,客户端与服务端之间关闭TCP的连接,如不关闭,就会导致性能上的损失
如上我们一直说到服务之间的交互,首先我们来谈同步交互,同步通信就是客户端向服务端发送请求后,服务端必须回应客户端
的的请求,所以它的缺陷也是非常明显的,也就是说服务端可能网络延迟的情况下,无法回应客户端,但是客户端在等待服务端
的回应,也就存在了超时,这也是同步通信中最大的缺陷。如下显示的是同步通信中的交互模式,如下所示:
由于同步通信的超时缺陷,以及在某些业务形态中,其实客户端发送请求后,并不需要服务端立刻马上有所回应的,比如下载
文件的业务,客户端发送请求后,下载文件需要一个过程,那么这个过程中,并不需要刻意的等待,客户端可以干其他的事,
这时候就可以使用到异步通信的模式,也就是说客户端与服务端并不需要知道对方的存在,更多主要关注的是MQ的机制,也
就使用到消息中间件,主流的消息中间件主要为RabbitMQ和Kafka(后期文章中针对这两个消息中间件会做系统权威的案例
解读)。我们还是通过交互图来看异步通信的模式,如下所示:
在如上中,可以看到客户端和服务端之间使用的是轻量级的MQ的中间件来进行交互。其实我们抛开客户端与服务端的角色,
其实在微服务架构这样的模式中,整个客户端发送请求后,它首先会经过API GateWay后,再发送给服务端,当然这个过程
它的链路是比较长的,具体交互如下:
当然在今天的文章体系中,我们主要讲的并不是这些理论的知识。但是有一点我们需要认可,也就是说理论指导实践,
而实践再来推导理论,这是一个完整的方法论体系。在具备如上的理论体系中,我们今天主要学习REST-Assured框架来
实现API的自动化测试,我们首先需要在maven中引入它,也就是pom.xml文件,在pom.xml文件中引入REST-Assured,
pom.xml文件的内容为:
<?xml version="1.0" encoding="UTF-8"?> <project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 "> <modelVersion>4.0.0</modelVersion> <groupId>org.example</groupId> <artifactId>ngApp</artifactId> <version>1.0-SNAPSHOT</version> <properties> <!--编译编码--> <project.build.sourceEncoding>UTF-8</project.build.sourceEncoding> <aspectj.version>1.8.10</aspectj.version> </properties> <dependencies> <dependency> <groupId>org.testng</groupId> <artifactId>testng</artifactId> <version>6.10</version> <scope>compile</scope> </dependency> <!--WebDriver的测试框架--> <dependency> <groupId>org.seleniumhq.selenium</groupId> <artifactId>selenium-java</artifactId> <version>3.141.59</version> </dependency> <dependency> <groupId>org.seleniumhq.selenium</groupId> <artifactId>selenium-server</artifactId> <version>3.141.59</version> </dependency> <!--引入Allure的框架--> <dependency> <groupId>io.qameta.allure</groupId> <artifactId>allure-testng</artifactId> <version>2.0-BETA14</version> <scope>test</scope> </dependency> <!--log4的模块--> <!-- https://mvnrepository.com/artifact/log4j/log4j --> <dependency> <groupId>log4j</groupId> <artifactId>log4j</artifactId> <version>1.2.17</version> </dependency> <!--fastjson库--> <!-- https://mvnrepository.com/artifact/com.alibaba/fastjson --> <dependency> <groupId>com.alibaba</groupId> <artifactId>fastjson</artifactId> <version>1.2.75</version> </dependency> <!--单元测试覆盖率信息--> <!-- https://mvnrepository.com/artifact/org.jacoco/jacoco-maven-plugin --> <dependency> <groupId>org.jacoco</groupId> <artifactId>jacoco-maven-plugin</artifactId> <version>0.8.6</version> <scope>test</scope> </dependency> <!--mockito框架--> <!-- https://mvnrepository.com/artifact/org.mockito/mockito-all --> <dependency> <groupId>org.mockito</groupId> <artifactId>mockito-all</artifactId> <version>1.10.19</version> <scope>test</scope> </dependency> <!--REST Assured框架--> <!-- https://mvnrepository.com/artifact/io.rest-assured/rest-assured --> <dependency> <groupId>io.rest-assured</groupId> <artifactId>rest-assured</artifactId> <version>4.3.3</version> <scope>test</scope> </dependency> </dependencies> <build> <plugins> <plugin> <groupId>org.apache.maven.plugins</groupId> <artifactId>maven-compiler-plugin</artifactId> <version>3.1</version> <configuration> <source>1.8</source> <target>1.8</target> <encoding>UTF-8</encoding> </configuration> </plugin> <!--Alure测试报告插件--> <plugin> <groupId>org.apache.maven.plugins</groupId> <artifactId>maven-surefire-plugin</artifactId> <version>2.20</version> <configuration> <argLine> -javaagent:"${settings.localRepository}/org/aspectj/aspectjweaver/${aspectj.version}/aspectjweaver-${aspectj.version}.jar" </argLine> <!--生成allure-result的目录--> <systemProperties> <property> <name>allure.results.directory</name> <value>./target/allure-results</value> </property> </systemProperties> </configuration> <dependencies> <dependency> <groupId>org.aspectj</groupId> <artifactId>aspectjweaver</artifactId> <version>${aspectj.version}</version> </dependency> </dependencies> </plugin> <!--检查代码覆盖率的插件配置--> <plugin> <groupId>org.jacoco</groupId> <artifactId>jacoco-maven-plugin</artifactId> <version>0.8.6</version> <executions> <execution> <id>prepare-agent</id> <goals> <goal>prepare-agent</goal> </goals> <configuration> <!--指定jacoco.exec的目录--> <destFile>target/jacoco.exec</destFile> <propertyName>jacocoArgLine</propertyName> </configuration> </execution> <execution> <id>check</id> <goals> <goal>check</goal> </goals> </execution> <execution> <id>report</id> <phase>prepare-package</phase> <goals> <goal>report</goal> </goals> </execution> </executions> <!-- Configuration 里面写配置信息 --> <configuration> <!-- rules里面指定覆盖规则 --> <rules> <rule implementation="org.jacoco.maven.RuleConfiguration"> <element>BUNDLE</element> <limits> <!-- 指定方法覆盖到80% --> <limit implementation="org.jacoco.report.check.Limit"> <counter>METHOD</counter> <value>COVEREDRATIO</value> <minimum>0.80</minimum> </limit> <!-- 指定指令覆盖到80% --> <limit implementation="org.jacoco.report.check.Limit"> <counter>INSTRUCTION</counter> <value>COVEREDRATIO</value> <minimum>0.80</minimum> </limit> <!-- 指定行覆盖到80% --> <limit implementation="org.jacoco.report.check.Limit"> <counter>LINE</counter> <value>COVEREDRATIO</value> <minimum>0.80</minimum> </limit> <!-- 指定类覆盖到100%,不能遗失任何类 --> <limit implementation="org.jacoco.report.check.Limit"> <counter>CLASS</counter> <value>MISSEDCOUNT</value> <maximum>0</maximum> </limit> </limits> </rule> </rules> </configuration> </plugin> <plugin> <groupId>org.apache.maven.plugins</groupId> <artifactId>maven-surefire-plugin</artifactId> <version>2.14.1</version> <configuration> <!--testng配置文件名称--> <suiteXmlFiles> <suiteXmlFile>testng.xml</suiteXmlFile> </suiteXmlFiles> <threadCount>1</threadCount> <parallel>tests</parallel> <!--测试失败后忽略继续执行--> <testFailureIgnore>true</testFailureIgnore> <skipTests>false</skipTests> <argLine>-Xmx256M ${jacocoArgLine}</argLine> </configuration> </plugin> </plugins> </build> </project>