Java 线上机器 CPU 100% 的一次排查过程

news2025/1/16 13:48:50

文章目录

  • 1. 问题发生
  • 2. 数据库连接关闭问题排查
  • 3. 问题的进一步排查
  • 4. 解决方法

1. 问题发生

日常敲代码突然收到生产环境异常告警,线上有一台机器 CPU 使用率飙升到 100 触发扩容,工作群里一下子鸡飞狗跳。 出现问题,首先当然是查看监控和日志,以下是相关现象:

  1. 从监控上看,CPU 飙升的同时,还伴随着大对象的分配和大量 GC

    在这里插入图片描述

  2. 紧接着搜索 Error 日志,发现问题时间点附近只有如下异常,显然是数据库连接关闭后又在连接上执行命令导致。公司有专门的 DBA 团队在维护数据库,直接带着问题去找人就好了

    org.springframework.jdbc.support.MetaDataAccessException: Error while extracting DatabaseMetaData; nested exception is com.mysql.jdbc.exceptions.jdbc4.MySQLNonTransientConnectionException: No operations allowed after connection closed.

2. 数据库连接关闭问题排查

DBA 的反馈是问题时间点附近有多个事务发生了并发更新锁等待,有事务长时间未提交,造成其他等待锁的事务超时,进而导致数据库主动关闭连接,除此之外就没有其他信息可以提供了。

此时排查整个项目代码,不存在多个触发点更新同一组表的情况,排除死锁。结合日志发现发生异常的接口短时间内被多次调用,每次调用都以异常结束,并且耗时都达到 10s 以上。根据操作日志和业务使用方联系上,证实对方使用一项功能时点击按钮没有反应,于是几秒内多次点击,直接导致了线上异常告警。至此,梳理线上故障产生的过程如下:

  1. 使用方点击按钮,发现没有反应(实际上是接口处理慢,没有返回),于是多次点击按钮触发接口调用,每次传过来的参数都一样
  2. 接口处理过程中发起了数据库事务,由于多次调用传入的参数都是一样的,所以最终是操作了同一组表的相同记录,存在并发更新锁的竞争
  3. 由于某些原因,首先发起数据库事务的线程处理缓慢,迟迟没有提交事务,导致其它线程发起的事务一直拿不到锁,直到超时后连接被数据库关闭,再在这个连接上发送命令就报出异常

经过以上梳理,显然造成数据库连接关闭问题的根因是从事务发起到事务提交两个节点之间存在耗时操作,导致事务长时间没有提交。到了这一步,基本锁定案发现场,结合代码和日志发现问题如下:

  1. 异常接口的处理逻辑中存在很多数据库操作,包括了表的更新和插入,事务范围比较大
  2. 业务使用方此次操作导致的数据变更量非常大,除了 10 张表数据更新,还包括了四万条数据的插入。由于四万条数据都是在内存中生成再一次插入数据库的,所以吃内存比较严重,可以和监控显示的大对象分配与频繁 GC 相映证

3. 问题的进一步排查

问题排查至此,似乎根本原因就是大事务,只要拆分事务就能解决。然而这其中依然存在一些疑点:

  1. 数据库插入四万数据是否会慢到 10s 的级别?程序中有打印 SQL 语句的组件,从 SQL 语句执行的日志来看,插入四万条数据其实不到 1s 就返回了
  2. 如果仅仅是数据库执行慢,那顶多也就是网络 IO 耗时,为什么 CPU 会飙到 100

公司基础设施还算完善,线上部署了 Arthas 用于排查问题,为了进一步排查,笔者决定复现问题,并同时使用 Arthas 实时监控程序运行状况。有关于 Arthas 的使用读者可以直接前往 官方传送门,笔者使用 thread -n 8 命令监控最忙的前 8 个线程,多次操作终于发现了 CPU 飙升 100 的罪魁祸首:

  1. 监控显示,最忙的线程的堆栈中正在执行的方法是字符串的匹配和替换,我们知道字符串匹配替换需要使用 CPU 资源
  2. 方法的触发点来自于 SQL 语句打印组件,该组件会切入 MyBatis 执行器,在数据库命令执行返回后打印 SQL,具体实现读者可以参考MyBatis @Intercepts 实现打印 SQL 语句
  3. 结合上一节分析,数据库执行了一条四万数据量的插入命令,SQL 语句庞大无匹,在此基础上通过字符串匹配替换实现 SQL 语句的参数填充,要消耗的 CPU 资源可想而知

4. 解决方法

分析到这里一切豁然开朗,解决方法自然不言而喻。由于 SQL 打印组件有开关配置属性,所以在生产环境改下这个属性关掉 SQL 打印功能,重新发布服务后问题解决,不再复现

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

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈,一经查实,立即删除!

相关文章

如何画架构图?

平时做过一些系统设计,也写过一些系统分析文章,从组件、关系、交互等方面提供一些建议,并用我之前写文章画的一些图举些例子。构成系统的组件通过形状、颜色、名称来逼近其概念。LevelDB 主要构件如上面 LevelDB 的架构图,包含的主…

Redis哨兵(Sentinel)

# Redis哨兵(Sentinel) Redis 的 Sentinel 系统用于管理多个 Redis 服务器(instance), 该系统执行以下三个任务: 监控(Monitoring): Sentinel 会不断地检查你的主服务器和从服务器是否运作正常…

内核参数 sched_min_granularity_ns 为什么看不到啦?

linux内核从版本v5.13-rc1起(含),sysctl 已无法设置 kernel.sched_min_granularity_ns。 其实不止sched_min_granularity_ns,在 /proc/sys/kernel 下,和CPU调度相关的6个参数都不见了: sched_latency_ns …

Unity VR开发教程 OpenXR+XR Interaction Toolkit 2.1.1(七)射线抓取

文章目录📕教程说明📕添加射线功能的相关组件📕设置 Interaction Layer Mask📕让 XR Direct Interactor 不对 XR Ray Interactor 产生干扰📕使抓取的物体不会吸到手上📕远距离抓取时通过摇杆改变抓取物体的…

Node.js安装及环境配置

Node.js安装及环境配置1.下载安装Node.js2.npm安装路径配置3.环境变量配置4.换源5.测试npm安装1.下载安装Node.js Node.js官网 下载如图所示版本:(请根据自己的系统环境选择) 下载完成后傻瓜式安装即可 测试环境: PS C:\Users…

终于拿到了爆火全网的进一线大厂程序员必看的1700道java面试题

爆火全网的进一线大厂程序员必看的1700道java面试题到底有多牛? 牛不牛不敢说,但是有好多程序员是靠这一套1700道高频面试题,顺利收到很多大厂offer! 以至于,到现在为止,大厂都开始按照这一套1700道面试题…

java计算机毕业设计ssm美食视频教学网站element 前后端分离

项目介绍 高校实验室信息管理平台是使用JAVA的SSM技术,MySQL作为数据库开发,用户通过查看实验室信息,在线预约实验室,实现高校实验室信息化管理。首先对本论文进行分析后,提出平台的相关技术,然后整理系统的需求分析,根据需求进行功能和数据库设计,最后进行系统实现和测试 。 …

Redis的Java客户端

目录 1 前言 2 Jedis客户端 2.1 jedis快速入门 2.2Jedis连接池 3 SpringDataRedis 3.1快速入门 3.2ReisTemplate配置序列化工具 3.3 StringRedisTemplate 1 前言 在Redis官网中提供了各种语言的客户端,地址:https://redis.io/resources/clien…

螺栓防松设计

常用的防松方法有三种:摩擦防松、机械防松和永久防松。机械防松和摩擦防松称为可拆卸防松,而永久防松称为不可拆卸防松。常用的永久防松有:点焊、铆接、粘合等,这种方法在拆卸时大多要破坏螺纹紧固件,无法重复使用。常…

系统测试-从研发到测试过程

系统测试是为了发现错误而执行程序的过程,成功的测试是发现了至今尚未发现的错误的测试。目的是在真实系统工作环境下通过与系统的需求定义作比较,检验完整的软件配置项能否和系统正确连接,发现软件与系统/子系统设计文档和软件开发合同规定不…

[Redis] Redis实战--EVAL

✨✨个人主页:沫洺的主页 📚📚系列专栏: 📖 JavaWeb专栏📖 JavaSE专栏 📖 Java基础专栏📖vue3专栏 📖MyBatis专栏📖Spring专栏📖SpringMVC专栏📖SpringBoot专…

基于移动品台的产品追溯系统设计与实现

项目描述 临近学期结束,还是毕业设计,你还在做java程序网络编程,期末作业,老师的作业要求觉得大了吗?不知道毕业设计该怎么办?网页功能的数量是否太多?没有合适的类型或系统?等等。这里根据疫情当下,你想解决的问…

骚戴独家笔试---算法篇

链表 反转链表 /* public class ListNode { int val; ListNode next null;ListNode(int val) { this.val val; } }*/ import java.util.Stack; public class Solution {public ListNode ReverseList(ListNode head) {Stack<ListNode> stack new Stack<>();//把…

进程间通信:无名管道+有名管道

进程间通信&#xff08;Inter-Process Communication&#xff09; 为什么需要进程间通信 当程序是多进程协同工作时&#xff0c;进程间基本都会涉及到数据共享 如何实现进程间数据的共享? 使用进程间通信来实现数据共享 进程间有时需要传递消息 --但是进程在系统有自己的地址…

msdn下载的系统怎么安装

有小伙伴们不知道安装msdn系统的具体操作&#xff0c;那么小编就教大家下载的系统怎么安装吧。 工具/原料&#xff1a; 系统版本&#xff1a;win10 专业版 品牌型号&#xff1a;联想小新Air 13 Pro 软件版本&#xff1a;小鱼一键重装系统v3.1.329.319 方法/步骤&#xff1…

UNIAPP实战项目笔记41 收货地址页面布局和省市县三级联动

UNIAPP实战项目笔记41 收货地址页面布局和省市县三级联动 my-add-path.vue 设置页面布局 具体内容图片自己替换哈&#xff0c;随便找了个图片的做示例 用到了vue的默认组件 城市选择器mpvueCityPicker,从uniappDemo中复制过来即可,具体位置见目录结构 代码 my-add-path.vue 页…

数据结构二叉排序树应用一

2022.11.19 二叉排序树应用一任务描述相关知识编程要求测试说明C/C代码任务描述 本关任务&#xff1a;输入一个无序序列&#xff0c;创建一棵二叉排序树。 相关知识 为了完成本关任务&#xff0c;你需要掌握&#xff1a;1.二叉排序树定义&#xff0c;2.如何创建一棵二叉排序…

黑*头条_第6章_admin端功能开发通用后端封装

黑*头条_第6章_admin端功能开发&通用后端封装 文章目录黑*头条_第6章_admin端功能开发&通用后端封装admin端功能开发&通用后端封装今日目标1 admin端的登录功能实现1.1 admin项目搭建1.2 登录接口-后端1.2.1接口定义1.2.2mapper定义1.2.3 代码编写1.3 前端项目导入…

FCN的代码解读

目录 模型初始化 VGG初始化 FCN初始化 图片的预处理 图片处理 图片编码 计算相关参数 模型训练 一个小问题 完整代码 参考 最近浅研究了一下关于图像领域的图像分割的相关知识&#xff0c;发现水还是挺深的&#xff0c;因为FCN差不多也是领域的开山鼻祖&#xff0c;所以就先从…

Postman进阶篇(十)-在pre-request script或test script中使用pm对象访问变量

在之前的文章中介绍过postman中的两个脚本——pre-request script或test script&#xff0c;在这两个脚本中都有使用到pm对象。&#xff08;pre-request script详细介绍、Test script详细介绍&#xff09;pm对象是在postman的脚本中非常重要&#xff0c;也是十分常用的方法。本…