一次java系统调优 从150到最高1800的过程

前言

在做公司系统压力测试(500个线程并发)的时候 某个服务的接口 压测初始结果如下
初始指标(最高):
吞吐量 150/s
TPS: 240
CPU,内存,带宽,磁盘io 如下图所示
image.png
image.png
image.png
可以看到资源使用是有问题的 cpu和带宽并没有给足压力 说明并不是资源所导致的瓶颈,所以现在分析代码

怎么分析代码在哪里耗时比较久呢?

主链路梳理
  1. 前置拦截器

    耗时节点次数
    查询缓存4
    查询数据库3
    刷新缓存2
    写数据库1
  2. 处理请求

    耗时节点次数
    查询数据库1
    查询缓存1
具体测试耗时分析
前置拦截器分析

通过arthas 分析 前置拦截器的每个耗时点的时间
利用trance 监听执行
image.png
监控结果如下 可以看出来是数据库写入是最耗时的
image.png

业务分析

这个写入数据库 我看到是非常简单的逻辑 就是记录api调用的次数
优化方案
一般写入数据库可以采用合并更新的方式减少写入的次数和访问db的次数
比如 一次访问记一次 优化成 访问一次将这次访问的记录放入到队列当中,然后消费者消费 和并次数 最终使用一次update来完成,当然了放到队列当中是有可能导致数据丢失,需要考虑业务是否允许容忍这部分的丢失,一切的技术都是服务于业务

处理请求节点分析

trace 截图如下 可以看到那次查询数据库是最为耗时的
image.png
继续查看那个耗时 方法
image.png
再继续分析
image.png

业务分析

这个是查询用户的数据
优化方案
是否可以添加缓存?

  1. 这部分数据不会经常变动,但是查询的却是比较频繁
  2. 和业务确认 这部分允许短时间内的数据不一致的情况 所以我们可以添加本地缓存。经过确认15分钟之内

优化

tomcat 参数优化(在下面的代码提升之后的参数调优)

提升这个参数并没有多大的提升 反而比默认的参数性能要差)是不是可以这么认为这个tomcat的参数并不是其性能点

tomcat:
  uri-encoding: UTF-8
  threads:
    #最大工作线程数,默认200, 4核8g内存,线程数经验值800
    #操作系统做线程之间的切换调度是有系统开销的,所以不是越多越好。
    max: 400
    # 最小工作空闲线程数,默认10, 适当增大一些,以便应对突然增长的访问量
    min-spare: 50
  # 等待队列长度,默认100
  accept-count: 300
  max-connections: 10000

默认参数与优化后的参数对比图

默认参数跑压测结果

1.默认参数吞吐量
2.默认参数TPS
3.默认参数的资源使用情况

优化后的参数跑压测结果对别

1.优化后参数 吞吐量
2.优化后参数tps
3.优化后资源使用情况

对比
类型接口平均响应值(毫秒)吞吐量/sTPS(平均)CPU 使用率带宽使用率占用内存
默认参数96748449090%3,000,0002G
优化后参数95148352090%3,000,0002G
结论

综合来看也就tps涨那么一丢丢 所以当前至少这个tomcat参数不是整个系统的瓶颈(不是关键瓶颈)。

再度优化

那到底什么是整个系统的瓶颈呢?
是不是还有可以做异步或者加缓存的代码节点没有发现? 我可以查看tomcat线程是不是有阻塞的,然后研究是不是可以做成异步,带着这个思路去看。
如何查看tomcat 线程是不是有阻塞?可以jstack 或者 arthas 查看
这里我选择arthas查看

查看当前最繁忙的10个线程
thread -n 10 

随机截取两个片段
1.txt2.txt
可以看到有一个rpc调用是一个阻塞点
image.png
一个日志打印也是阻塞点(这个阻塞点还不少 所以优化日志打印或者关闭日志打印)
image.png

日志打印优化

优化代码

if (logger.isTraceEnabled()) {
    logger.trace("Using MessageSource [" + this.messageSource + "]");
}
logger.trace("Using MessageSource [" + this.messageSource + "]");

配置优化
直接error级别的日志打印
结果如下
1.最高吞吐量截图
2.TPS截图
3.资源使用截图
620A6CC7.png居然提升这么多 吓人,简直起飞
虽然部分时间段非常非常高,但是最终趋于稳定 大概提升 15%左右 由此可见日志也不能乱打印 需要打印有效日志 或者选一个好一点的非阻塞式日志框架 这个logback性能还是有点问题

rpc调用添加缓存

这个时候我们给那个rpc调用阻塞点 添加一个缓存 查看效果
image.png
挖槽最高吞吐量居然达到了 1800/s, 此时此刻我只想吟诗一首
代码神手,优化奇才,
调和阴阳,掌舵未来。
从百倍速,至于千倍速,
跃然纸上,效能飙升。
最高吞吐量
稳定的平均吞吐量
TPS
资源使用情况

核心流程代码优化

合并api请求次数入库的核心代码如下 通过添加一个countEmpty来提高合并的成功率 不然还是update操作时太少了几乎还是1
image.png

优化前后对比

类型接口平均响应值(毫秒)最高吞吐量/s吞吐量/sTPS(平均)CPU 使用率带宽使用率占用内存
优化前223220015318060%1500,0002G
优化后643181162380040%500,0002G

一些小的提升没想到居然如此之大。所以还是好好写代码,写好代码吧。

难道就优化到这里了吗?

是不是还忘记了啥?JVM还没有优化,内存还没有优化,数据还没有优化
再次用arthas 查看程序的阻塞点还有哪些?
可以看到 tomcat的线程有一些在等待队列当中的任务。
image.png
并没有查看到一些阻塞点,怎么办 还能提升吗?

  1. 查看程序有没有进行垃圾回收(这个是java程序源优化时必须要关注的点)
  2. 提升一下内存看是否有效
  3. 再次修改tomcat参数 但是这一点我认为已经没有必要了 因为有一部分tomcat的线程还是空闲状态,并没有在跑,所以他还不是满压状态。所以排除这一点。
有没有进行垃圾回收?

image.png
可以看到使用的是 Parallel Scavenge 垃圾回收器

  1. gc.ps_scavenge.count:垃圾回收次数
  2. gc.ps_scavenge.time(ms):垃圾回收消耗时间
  3. gc.ps_marksweep.count:标记-清除算法的次数
  4. gc.ps_marksweep.time(ms):标记-清除算法的消耗时间
    Parallel Scavenge收集器的特点是它的关注点与其他收集器不同,CMS等收集器的关注点是尽可能 地缩短垃圾收集时用户线程的停顿时间,而Parallel Scavenge收集器的目标则是达到一个可控制的吞吐量.(Throughput)。所谓吞吐量就是处理器用于运行用户代码的时间与处理器总消耗时间的比值。
    如果虚拟机完成某个任务,用户代码加上垃圾收集总共耗费了100分钟,其中垃圾收集花掉1分 钟,那吞吐量就是99%。停顿时间越短就越适合需要与用户交互或需要保证服务响应质量的程序,良 好的响应速度能提升用户体验;而高吞吐量则可以最高效率地利用处理器资源,尽快完成程序的运算 任务,主要适合在后台运算而不需要太多交互的分析任务。 Parallel Scavenge收集器提供了两个参数用于精确控制吞吐量,分别是控制最大垃圾收集停顿时间 的-XX:MaxGCPauseMillis参数以及直接设置吞吐量大小的-XX:GCTimeRatio参数  。

是否可以减少垃圾回收次数?
由于他是回收老年代又是与用户线程并发执行的垃圾回收器 几乎不会停顿用户线程,所以这个垃圾回收影响程序不大。并且此时并没有触发FULL GC,所以貌似没有优化点 可以尝试一下 使用新的垃圾收集器G1看是否有提升(我认为提升应该不大 G1对大内存的垃圾回收有优势)。
果然几乎没有提升
吞吐量
TPS
资源使用

提升内存试试

同样的并没有较大的提升,图就不贴了,所以我认为现在的问题就是我发的不够快 我的测试并发量不够

提升并发量试试(1000个线程)

1.平均吞吐量
2.TPS
3.资源使用情况
貌似并不是我们想的那样啊,并不是我发的不够快
再次通过arthas 看看1000的并发下 tomcat线程在干啥 有没有阻塞的
通过下面来看 还是和500并发的一样 有部分线程还是waiting
image.png
这个是为啥呢?我想这个资源貌似没有用到极致例如cpu和带宽,还有内存
我认为是我还是发的不够快 ,所以我决定搭建一个Jmeter集群来进行压测。
3台 jmeter worker节点
1.平均吞吐量
2.TPS
资源使用
可以看到cpu已经几乎到顶了,貌似没有啥优化点了。
done

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:/a/162386.html

如若内容造成侵权/违法违规/事实不符,请联系我们进行投诉反馈qq邮箱809451989@qq.com,一经查实,立即删除!

相关文章

代码随想录算法训练营第三十九天【动态规划part02】 | 62.不同路径、63. 不同路径 II

62.不同路径 题目链接: 力扣(LeetCode)官网 - 全球极客挚爱的技术成长平台 求解思路: 动规五部曲 确定dp数组及其下标含义:dp[i][j] 表示从(0,0)出发,到(i,j&#x…

计算机科学速成课

建议看看计算机科学速成课,一门很全面的计算机原理入门课程,短短10分钟可以把大学老师十几节课讲的东西讲清楚!整个系列一共41个视频,B站上有中文字幕版。 每个视频都是一个特定的主题,例如软件工程、人工智能、操作系…

Django的可重用HTML模板示例

01-配置并运行Django项目 首先按照博文 https://blog.csdn.net/wenhao_ir/article/details/131166889配置并运行Django项目。 02-创建可重用模板文件 templates目录下新建目录common,然后在目录common下新建文件:navbar.html,并写入下面的…

Pandas 求平均值

Pandas是Python中最流行的数据分析库之一,它提供了许多强大的工具来处理和分析数据集。其中,求平均值是数据分析中最常见的操作之一。在本文中,我们将从多个角度分析Pandas中如何求平均值。 一、基础操作 Pandas中求平均值的基础操作是使用m…

电磁场与电磁波part3--静态电磁场及其边值问题的解

1、当场源(电荷、电流)不随时间变化时,所产生的电场、磁场也不随时间变化,称为静态电磁场。静止电荷产生的静电场、在导电媒质中恒定运动电荷形成的恒定电场以及恒定电流产生的恒定磁场都属于静态电磁场。 2、静电场基本方程微分形…

深信服AC应用控制技术

拓扑图 目录 拓扑图 一.上班时间不允许使用qq(假设上班时间是上午9到12,下午14到18) 1.新增上班时间不允许使用qq访问权限策略 2.将策略应用到组,例如修仙部 3.验证 上班时间发现登录不了 下班时间可以登录 二.上班时间不允许访问视频网站(假设上班时…

springboot323基于Java的美妆购物网站的设计与实现

交流学习: 更多项目: 全网最全的Java成品项目列表 https://docs.qq.com/doc/DUXdsVlhIdVlsemdX 演示 项目功能演示: ————————————————

梦想编织者——Adobe Dreamweaver

今天,我们来谈谈一款在Adobe系列中推出的一款Adobe Dreamweaver,简称“DW”,中文名称 “梦想编织者”,是集网页制作和管理网站于一身的所见即所得网页代码编辑器。 利用对 HTML、CSS、JavaScript等内容的支持,设计人员…

java并发编程JUC:一、专栏配置+进程与线程+并行和并发+同步和异步+线程的创建、调用、查看、运行原理和相关API

专栏配置 pom.xml <properties><maven.compiler.source>1.8</maven.compiler.source><maven.compiler.target>1.8</maven.compiler.target> </properties> <dependencies><dependency><groupId>org.projectlombok<…

(论文阅读46-50)图像描述2

46.文献阅读笔记 简介 题目 Learning a Recurrent Visual Representation for Image Caption Generation 作者 Xinlei Chen, C. Lawrence Zitnick, arXiv:1411.5654. 原文链接 http://www.cs.cmu.edu/~xinleic/papers/cvpr15_rnn.pdf 关键词 2014年rnn图像特征和文本特…

目录自动清洗

文章目录 前言一、需求分析二、操作步骤详解&#xff08;标准章节&#xff09;1. 提取文章目录2. 更改保存目录.txt3. 二级标题前面加4个空格4. 在章字和节字后面添加一个空格5. 在页码前面加上>符号6. 代码完全体 三、进阶一&#xff08;有章无节小数二级标题&#xff09;1…

git基础命令

git简介 什么是git&#xff1f; git是一种分布式版本控制系统。 git与svn之间的区别是什么&#xff1f; svn是集中式版本控制系统。git是分布式版本控制系统。 什么是集中式版本控制系统&#xff1f;有哪些特点&#xff1f; 版本库是集中存放在中央服务器。集中式版本控制…

kk模组的具体应用场合

KK模组是一种高精度、高刚度的直线模组&#xff0c;广泛应用于各种自动化设备和精密仪器中。以下是KK模组的一些具体应用场合&#xff1a; 1、半导体设备&#xff1a;半导体制造过程中需要使用精密的定位和运动控制设备&#xff0c;KK模组作为一种高精度、高刚度的直线模组&…

Selenium——利用input标签上传文件

Selenium利用input标签上传文件 完整流程 打开文件上传页面选择要上传的文件点击上传按钮确认文件上传成功介绍怎么方便的获取对应元素的Xpath或者Css 简单介绍 在使用Selenium进行浏览器自动化测试时&#xff0c;文件上传是一个常见的需求。而 标签就是实现文件上传功能的…

【Python自动化】定时自动采集,并发送微信告警通知,全流程案例讲解!

文章目录 一、概要二、效果演示三、代码讲解3.1 爬虫采集行政处罚数据3.2 存MySQL数据库3.3 发送告警邮件&微信通知3.4 定时机制 四、总结 一、概要 您好&#xff01;我是马哥python说&#xff0c;一名10年程序猿。 我原创开发了一套定时自动化爬取方案&#xff0c;完整开…

十一、统一网关GateWay(搭建网关、过滤器、跨越解决)

目录 一、网关技术的实现 在SpringCloud中网关的实现包括两种: 作用&#xff1a; 二、搭建网关服务 1、新建模块&#xff0c;并添加依赖 2、新建Gateway包&#xff0c;并编写启动类 3、编写yml文件 4、启动服务&#xff0c;并在网页内测试 5、步骤 三、路由断言工厂 …

Python与ArcGIS系列(九)自定义python地理处理工具

目录 0 简述1 创建自定义地理处理工具2 创建python工具箱0 简述 在arcgis中可以进行自定义工具箱,将脚本嵌入到自定义的可交互窗口工具中。本篇将介绍如何利用arcpy实现创建自定义地理处理工具以及创建python工具箱。 1 创建自定义地理处理工具 在arctoolbox中的自定义工具箱…

C++初阶 日期类的实现(下)

目录 一、输入输出(>>,<<)重载的实现 1.1初始版 1.2友元并修改 1.2.1简单介绍下友元 1.2.2修改 1.3>>重载 二、条件判断操作符的实现 2.1操作符的实现 2.2!操作符的实现 2.3>操作符的实现 2.4>,<,<操作符的实现 三、日期-日期的实现 …

Flutter笔记:Matrix4矩阵变换与案例

Flutter笔记 Matrix4矩阵变换及其案例 作者&#xff1a;李俊才 &#xff08;jcLee95&#xff09;&#xff1a;https://blog.csdn.net/qq_28550263 邮箱 &#xff1a;291148484163.com 本文地址&#xff1a;https://blog.csdn.net/qq_28550263/article/details/134474764 【简介…