性能与压力测试
@[toc]
一、性能监控
1、jvm内存模型

- 程序计数器 Program Counter Register:
- 记录的是正在执行的虚拟机字节码指令的地址
- 此内存区域是唯一一个在JAVA虚拟机规范中没有规定任何OutOfMemoryError的区域
- 虚拟机栈 VMStack:
2、堆
所有的对象实例以及数组都要在堆上分配。堆是垃圾收集器管理的主要区域,也被称为”GC堆”;也是我们优化最多考虑的地方。堆可以细分为:
新生代Eden空间From Survivor空间To Survivor空间
老年代永久代/元空间- Java8以前永久代,受jvm管理, java8以后元空间,直接使用物理内存。因此,默认情况下,元空间的大小仅受本地内存限制。
垃圾回收

从Java8开始, Hotspot已经完全将永久代(Permanent Generation)移除,取而代之的是个新的区域一元空间(MetaSpace)
3、jconsole与jvisualvm
JDK 的两个小工具 jconsole、jvisualvm(升级版的jconsole) ;通过命令行启动,可监控本地和远程应用。远程应用需要配置
jconsole:






1、jvisualvm能干什么
监控内存泄露,跟踪垃圾回收,执行时内存、cpu分析,线程分析
启动jvisualvm:


监控内存泄露, 跟踪垃圾回收, 执行时内存、 cpu分析: 
线程分析:

运行: 正在运行的休眠: sleep等待: wait驻留: 线程池里面的空闲线程监视: 阻塞的线程,正在等待锁
2、安装插件方便查看 GC
cmd启动jvisualvm工具→插件
- 如果503错误解决:
- 打开网址 visualvm.github.io/pluginscent…
- cmd 查看自己的 jdk 版本,找到对应的


安装完插件需要重启 jvisualvm

4、监控指标
开发环境配置:
实体机: 开发和服务运行

虚拟机: 运行中间件和数据库,内存3G,1核
CentOS-7、Docker、redis、mysql:5.7、elasticsearch:7.4.2、kibana:7.4.2、nginx:1.10
1、中间件指标
nginx:
- 计算型
- 消耗cpu



Gateway:
- 计算型
- 比较消耗cpu




2、数据库指标
- SQL耗时越小越好,一般情况下微秒级别。
- 命中率越高越好,一般情况下不能低于95%
- 锁等待次数越低越好,等待时间越短越好。
服务压测:
简单服务(不请求数据库):





Gateway+简单服务(不请求数据库):



全链路(不请求数据库):


首页一级菜单渲染(不过网关):



三级分类数据获取:


首页全量数据获取:



Nginx+Gateway:
结果汇总:
| 压测内容 | 压测线程数 | 吞吐量/s | 90%响应时间 | 99%响应时间 |
|---|---|---|---|---|
| Nginx | 50 | 6564 | 4ms | 172ms |
| Gateway | 50 | 12356 | 6 | 19 |
| 简单服务 | 50 | 14177 | 4 | 65 |
| 首页一级菜单渲染(未开thymeleaf缓存) | 50 | 515 | 130 | 200 |
首页一级菜单渲染(开启thymeleaf缓存、优化数据库、关日志) |
50 | 607/700 |
101/86 |
118/151 |
| 三级分类数据获取 | 50 | 5/19(加索引) |
11141/2764 |
11366/2956 |
| 三级分类数据获取(业务逻辑优化) | 50 | 200 | 398 | 644 |
| 三级分类数据获取(使用redis缓存) | 50 | 684 | 95 | 128 |
首页全量数据获取(优化前/优化后/动静分离后) |
50 | 20/22/550 |
3426/2522/103 |
4272/3133/804 |
| Nginx+Gateway | 50 | |||
| Gateway+简单服务 | 50 | 4919 | 21 | 47 |
| 全链路 | 50 | 1439 | 50 | 80 |
简单服务:慢的原因,一是DB,二是thymeleaf渲染。通过对比可以看到:
首页一级菜单渲染在开启thymeleaf缓存前后吞吐性能提升约17.86%,还是比较明显的。首页一级菜单渲染访问的时候,在关闭debug日志和给where条件列加索引之后,DB请求耗时从原来的6-1085ms,提升至2-8ms,速度提升3-135倍。首页一级菜单渲染在开启thymeleaf缓存、优化数据库(加索引)、关日志之前和之后的对比可以看到吞吐量提升约35.92%。
三级分类数据获取:慢的原因,主要是DB,存在遍历查询,多次请求服务的过程,数据库IO频繁,开发环境未关闭debug级别的日志;目前服务尚未使用数据库连接池,可配置数据库连接池进行优化,另外对于三级分类这种不会经常变动的数据,可以选择使用redis缓存起来来提高访问的效率。
首页全量数据获取:慢的原因,通过和首页一级菜单渲染进行对比可以知道,慢的原因主要是静态资源加载慢;目前我们的服务尚未做动静资源的请求分离操作,可以使用nginx做静态资源服务器来进行优化。
结论及优化:
中间件越多,性能损失越大,大多都损失在网络交互。可以优化中间件配置,使用更快的硬件资源业务:- DB(MySQL服务优化,索引优化)
- 模板的渲染速度(thymeleaf开发期间是关闭缓存的,服务上线后要开启缓存;模板渲染需要CPU去计算,所以可以使用更好的CPU;服务器内存)
- 静态资源
5、 JVM 分析&调优
1、几个常用工具
2、命令示例
3、调优项
1、性能压测-优化-nginx动静分离

1)上传静态资源到nginx服务器
- 在/
mydata/nginx/html/路径下创建static/文件夹 - 将本地代码路径中的
src\main\resources\static文件夹下的静态资源文件全部上传到nginx服务器中。
2)修改nginx配置文件并重启
- 修改从nginx的
conf.d目录中的default.conf文件复制的pafcmall.conf文件,在location / {之前添加静态资源文件访问路径配置:
# 配置静态资源访问路径
location /static/ {
root /usr/share/nginx/html;
}
- 重启nginx:
docker restart nginx
3)修改本地代码,删除本地代码路径中的src\main\resources\static文件夹下的静态资源文件,同时修改index.html文件中对静态资源的引用路径。
js:
<script src="/static/index/js/xxx.js" type="text/javascript" charset="utf-8"></script>
css:
<link rel="stylesheet" href="/static/index/css/xxx.css">
img:
<img src="/static/index/img/xxx.jpg" />
2、性能压测-优化-模拟线上应用内存崩溃宕机情况
1、JVM调优-设置商品服务启动参数进行比较,都以50个线程为例:
1)-Xmx100m


2)-Xmx512m
设置堆内存最大大小为512m


3)-Xmx1024m -Xms1024m -Xmn512m
设置堆内存最大和最小大小为1024m;并设置新生代(Eden+S0+S1)为512m,减少垃圾回收器进行频繁的Minor GC


2、模拟线上应用内存崩溃宕机情况
将jmeter的线程数设置到200,将服务的最大堆内存设置到-Xmx100m,进行模拟测试: 服务不可用:

OOM异常:

3、性能压测-优化-优化三级分类数据获取
将数据库多次查询变为一次查询,减少数据库频繁IO,可以看到50个线程,Xmx为100m的情况下,服务的吞吐量达到了200,相比之前图标中只加索引的19,性能提升约10倍。

如果还想要进一步提升性能,就需要考虑使用数据库连接池、使用缓存的情况,这个会在后面介绍到。
二、压力测试
压力测试:
压力测试考察当前软硬件环境下系统所能承受的
最大负荷并帮助找出系统瓶颈所在。压测都是为了系统在线上的处理能力和稳定性维持在一个标准范围内,做到心中有数。使用压力测试,我们有希望找到很多种用其他测试方法更难发现的错误。有两种错误类型是:
内存泄漏,并发与同步。有效的压力测试系统将应用以下这些关键条件
重复,并发,量级,随机变化。
1、性能指标
- 响应时间(Response Time:RT):响应时间指用户从客户端发起一个请求开始,到客户端接收到从服务器端返回的响应结束,整个过程所耗费的时间。
- HPS (Hits Per Second) :每秒点击次数,单位是次秒。
TPS (Transaction per Second):系统每秒处理交易数,单位是笔/秒。QPS (Query per Second):系统每秒处理查询次数,单位是次/秒。对于互联网业务中,如果某些业务有且仅有一个请求连接,那么TPS=QPS=HPS,般情况下用TPS来衡量整个业务流程,用QPS来衡量接口查询次数,用HPS来表示对服务器单击请求。
-
无论TPS、 QPS、 HPS,此指标是衡量系统处理能力非常重要的指标,越大越好,根据经验,一般情况下:
金融行业: 1000TPS~50000TPS,不包括互联网化的活动保险行业: 100TPS~100000TPS, 不包括互联网化的活动制造行业: 10TPS~5000TPS互联网电子商务: 10000TPS-1000000TPS互联网中型网站: 1000TPS-50000TPS互联网小型网站: 500TPSM10000TPS - 最大响应时间(Max Response Time):指用户发出请求或者指令到系统做出反应(响应)的最大时间。
- 最少响应时间(Mninum ResponseTime):指用户发出请求或者指令到系统做出反应(响应)的最少时间。90%响应时间(90% Response Time)是指所有用户的响应时间进行排序,第90%的响应时间。
-
从外部看,性能测试主要关注如下三个指标:
吞吐量:每秒钟系统能够处理的请求数、任务数。响应时间:服务处理一个请求或一个任务的耗时。错误率:一批请求中结果出错的请求所占比例。
2、JMeter
1、JMeter安装
jmeter.apache.org/download_jm… 下载对应的压缩包,解压运行 jmeter.bat 即可
2、JMeter压测示例
添加线程组——添加请求数:


添加取样器——添加请求接口:


添加监听器——观察执行结果:


3、JMeter Address Already in use 错误解决
windows 本身提供的端口访问机制的问题。
Windows提供给TCP/IP链接的端口为 1024-5000,并且要四分钟来循环回收他们。就导致我们在短时间内跑大量的请求时将端口占满了。
1、cmd 中,用 regedit 命令打开注册表
2、在 HKEY_LOCAL_MACHINE\SYSTEM\CurrentControlSet\Services\Tcpip\Parameters 下
1,右击
parameters,添加一个新的DWORD,名字为MaxUserPor2、然后双击
MaxUserPort,输入数值数据为65534,基数选择十进制(如果是分布式运行的话,控制机器和负载机器都需要这样操作哦)
3,修改配置完毕之后记得重启机器才会生效
support.microsoft.com/zh-cn/help/…
TCPTimedWaitDelay: 30