性能测试有两种类型,负载测试和压力测试:
压测时重点关注的指标:并发用户数、TPS(每秒事务数量)、RT(事务响应时间)、事务失败率、吞吐量、CPU(不要超过70%)和内存占用量。
注意事项:
负载测试
性能测试时重点关注的指标数据:
总结
一般情况是没有必要严格区别压力测试和负载测试,他们的目标都是为了评估系统的极限工作状态或者发现系统的性能瓶颈进一步做系统性能优化,下面列举的工具一般情况下对这两种测试场景都是支持的。
性能测试,看要测试什么对象,如代码的执行性能,接口的耗时,单机的承载,DB的读写极限等,根据不同的待压测对象使用不同的工具:;
应用类型,
CPU密集型应用
IO密集型应用
官网
桌面应用程序,用户界面采用Swing Java API实现,故而跨平台。可扩展的,提供大量的可用插件。
Samplers,用于发送请求到不同类型的服务器。它们是每一个测试计划的基本要素,采样器执行基于配置请求。JMeter 5.1.1可用的采样器列表:
访问日志采样器、AJP采样器、Bean shell取样器、BSF采样器、调试采样器、FTP采样器、HTTP采样器、Java采样器、JDBC采样器、JMS(几个)采样器、JSR223采样器、JUnit采样器、LDAP采样器、邮件阅读器、MongoDB采样器、操作系统进程取样器、SMTP采样器、SOAP、TCP采样器、测试行动。
存在多种其他不同于JMeter插件的实现技术。每个采样器的配置取决于它所执行的请求;这意味着一些采样器有一些共性的配置,而另外一些采样器由于它们各自请求的不同而完全不同。
Logic Controllers,允许你配置一个线程组内不同采样器的执行顺序。可用的逻辑控制器:
简单控制器、循环控制器、一次性控制器、交错控制器、随机控制器、随机顺序控制器、流量控制器、运行时控制器、If控制器、While控制器、Switch控制器、ForEach控制器、模块控制器、include控制器、事务控制器、记录控制器
Listeners,提供不同的方式查看由采样器请求产生的结果。监听器以报表、树型结构、或简明的日志文件的形式分析结果。还可以在测试计划中的任何地方添加监听器,但他们只会在各自的应用范围内解析和收集来自采样器的数据。可用的监听器:
样品结果配置保存、全图景结果集、图表结果集、样条线可视化工具、断言结果集、树形结果集、整合报告、表格结果集、简单数据输出、监测结果集、分布图(alpha)、整合图、Mailer可视化工具、Beanshell监听器
Timers,用来定义请求之间的等待时间。如果不指定,JMeter会一个请求完成后立即执行下一个请求,没有任何等待时间。可用的计时器:
恒定的定时器、高斯随机定时器、均匀随机定时器、恒定吞吐量定时器、同步定时器、jsr223定时器、Beanshell定时器、BSF定时器、泊松随机定时器
Assertions,通过验证采样器请求产生的响应,来验证测试计划的有效性。用来检测被测试应用程序的响应质量。你可以为每个测试计划配置任何生效的断言。可用的断言列表:
Bean shell断言、BSF断言、比较断言、jsr223断言、响应断言、Duration断言、XML Assertion、BeanShell Assertion、MD5Hex Assertion、HTML Assertion、XPath Assertion、XML Schema、Assertion
官网:https://gatling.io/
Load test as code
使用Scala语言,从代码级别支持性能测试,能生成丰富多彩的报告,包含测试案例中收集的所有指标。同时提供脚本从命令行运行性能测试,支持录制(record)功能。
<dependency>
<groupId>io.gatlinggroupId>
<artifactId>gatling-coreartifactId>
<version>3.3.1version>
dependency>
每一个Gatling测试都要继承 Simulation 类:
import io.gatling.core.Predef._
import io.gatling.http.Predef._
import scala.concurrent.duration._
class ApiGatlingSimulationTest extends Simulation {
// 定义protocol
val httpProtocol = http
.baseUrl("http://computer-database.gatling.io") // root URL for all relative URLs
.acceptHeader("text/html,application/xhtml+xml;q=0.9,*/*;q=0.8") // common headers
.doNotTrackHeader("1")
.acceptLanguageHeader("en-US,en;q=0.5")
.acceptEncodingHeader("gzip, deflate")
.userAgentHeader("Mozilla/5.0 (Macintosh; Intel Mac OS X 10.8; rv:16.0) Gecko/20100101 Firefox/16.0")
// 一个repeat对应一次模拟测试,使用{
}
val scn = scenario("InjectAndGet").repeat(1000, "n") {
exec(
http("AddPerson-API")
.post("http://localhost:8080/api")
.header("Content-Type", "application/json")
.body(StringBody("""{"firstName":"John${
n}","lastName":"Smith${
n}","birthDate":"1980-01-01", "address":{"country":"pl","city":"Warsaw","street":"Test${
n}","postalCode":"02-200","houseNo":${n}}}"""))
.check(status.is(200))
)
// 还支持这种方式:.pause(629 milliseconds)
.pause(Duration.apply(5, TimeUnit.MILLISECONDS))
}.repeat(1000, "n") {
exec(
http("GetPerson-API")
.get("http://localhost:8080/api/${n}")
.check(status.is(200))
)
}
// 30个并发用户&测试10min
setUp(scn.inject(atOnceUsers(30))).maxDuration(FiniteDuration.apply(10, "minutes")
//.protocols(httpProtocol)
)
}
对于POST请求,除body.StringBody()
这种方式之外,还有formParam
:
.exec(
http("post-demo")
.post("/api")
.formParam("name", "Beautiful Computer") // Note the triple double quotes: used in Scala for protecting a whole chain of characters (no need for backslash)
.formParam("introduced", "2012-05-30")
)
配置maven插件:
<build>
<plugins>
<plugin>
<groupId>io.gatlinggroupId>
<artifactId>gatling-maven-pluginartifactId>
<version>${gatling-plugin.version}version>
<configuration>
<simulationClass>com.anoyi.test.ApiGatlingSimulationTestsimulationClass>
<resultsFolder>/Users/admin/code/gatlingresultsFolder>
configuration>
plugin>
plugins>
build>
执行命令:mvn gatling:execute
,生成的所有HTML报告都可以在performance-test/build/gatling-results
目录下找到
Apache Benchmark,统计功能强大。默认使用GET方法测试,
Ubuntu安装:sudo apt-get install apache2-utils
Redhat安装:yum -y install httpd-tools
命令格式:ab -n 100 -c 10 'http://10.34.216.49:8000/test'
常用参数:
-c,concurrency,测试并发度,即连接数
-t,测试时间,此时默认-n默认为50000
-n,测试请求次数,一般-t或-n选一个
-p,postfile,读取json文本request,需要一并使用-T
-u ,putfile,发送PUT请求时需要上传的文件,需要一并使用-T
-T,Content-Type,指明请求数据格式
示例:
# 如果只用到一个Cookie,那么只需键入命令:
ab -n 100 -C key=value http://test.com/
# 如果需要多个Cookie,就直接设Header:
ab -n 100 -H "Cookie: Key1=Value1; Key2=Value2" http://test.com/
比较重要的返回信息:
信息 | 示例 | 解读 |
---|---|---|
Concurrency Level | 1000 | 并发数 |
Time per request(mean) | 465.338[ms] | 所有并发用户都请求一次的平均时间 |
Time request | 0.247[ms] | 单个用户请求一次的平均时间,计算全部次数的均值 |
Requests per second(mean) | 2148 | 平均每秒请求数,服务器的吞吐量 |
Percentage of the requests served within a certain time(ms) | 95% 846 | 95%的请求在846ms内返回,可看95线,99线 |
测试POST方法时,requestBody一般是json文本,需要放入txt格式文件中,且以''
括起来,使用-p -T
。
测试遇到:socket: Too many open files
时,需调整可打开文件数:ulimit -n 20480
问题:
官网:https://github.com/wg/wrk
wrk 只能运行在类Unix 的系统上。
git clone源码make编译,make成功后同目录生成wrk文件,可复制到bin目录。
使用:
wrk <选项> <被测HTTP服务的URL>
-c, --connections,跟服务器建立并保持的TCP连接数量
-d, --duration,压测时间
-t,--threads,配置线程
-s, --script,指定Lua脚本路径
-H, --header,为每一个HTTP请求添加HTTP头
--latency,在压测结束后打印延迟统计信息
--timeout,超时时间
-v,--version打印正在使用的wrk的详细版本信息
# 其中数字参数,支持国际单位 (1k, 1M, 1G)
# 其中时间参数,支持时间单位 (2s, 2m, 2h)
示例:
wrk -t8 -c200 -d30s --latency "http://www.baidu.com"
官网:http://www.joedog.org/
一款HTTP/HTTPS负载测试和基准测试工具,支持基本身份验证、Cookie、HTTP、HTTPS和FTP协议,可配置模拟并发用户数。
安装:yum install siege -y
安装成功与否,查看版本:siege -V
help文档:
siege --help
-C, --config:查看siege当前的配置信息
-V, --version:版权说明信息
-c, --concurrent=NUM:并行启动(访问)用户数,默认是10
-t, --time=NUMm:压力测试时间,比如-t5表示持续时间是5分钟
-b, --benchmark:基准测试,请求之间没有延迟。
-g, --get get方式请求
-d, --delay=NUM 时间延迟,每个请求之间的延迟时间
-i, --internet 模拟用户,随机点击的URL
-r, --reps=NUM:每个连接发出的请求数量,与t有些类似,两者设置一个即可
-f, --file=FILE:对应一个文件,这个文件里每一行为一个URL链接,格式如:
-m, --mark="text" 在日志里标记的字符串标识
-H, --header="text" 在Header里增加的字符串标识
-A, --user-agent="text" 在user-agent里增加的字符串标识
-u, --url="URL",设置被测Web的URL
举例:10个并发,每个连接10个请求,间隔1秒请求压测。
siege -u www.baidu.com -d1 -r10 -c 10
HTTP/1.1 200 0.05 secs: 143913 bytes ==> GET /static/superman/js/lib/jquery-1-cc52697ab1.10.2.js
Transactions: 1017 hits // 总处理数量
Availability: 100.00 % // 成功请求百分百
Elapsed time: 10.06 secs //总耗时
Data transferred: 35.65 MB //总传输数据量
Response time: 0.03 secs // 响应时间
Transaction rate: 101.09 trans/sec // 每秒处理请求数
Throughput: 3.54 MB/sec // 吞吐量
Concurrency: 3.38 // 并发数
Successful transactions: 1017 //成功处理次数
Failed transactions: 0 //请求失败数
Longest transaction: 0.33 // 请求最长耗时
Shortest transaction: 0.00 //请求最短耗时
使用python语言写的分布式的压测工具,GitHub,有示例examples。
官网说明:
Define user behaviour with Python code, and swarm your system with millions of simultaneous users.
安装方式其一:pip install locustio
Locust依赖python模块:
Locust压力测试使用总结
Locust压测框架入门
模块化,跨平台以及多线程的DB性能测试工具
Web开发的各种性能工具