MySQL优化实战 解决CPU100%

news2024/11/24 1:14:43

问题表象

在24年初有一个日经问题困扰着我们,每到正点03分DB的CPU开始打满,持续1分钟又恢复正常水平。但由于日常业务交付压力较大且权限限制没有登录DB主机的权限,大家也就得过且过一直没有去认真排查。直到某天我来兴趣了也有时间了,就想起这个问题开始深入排查一下尝试解决。

排查-可能的问题点

这种一看周期性非常规律的CPU打满,又很快回落到正常水平的现象,有经验的就会猜到是定时任务导致的。的确这是一个大概率的猜测方向。但还有另一个可能,在做活动也会有周期性的流量暴增情况,但我们系统是to b的业务系统所以排除。

结合定时任务分析有2种可能,这个从Job的执行时间频率上能看出来。然后通过业务逻辑大致可以知道哪一个Job是比较重的结合时间重点排查。在我们系统中有一个核心业务,每小时会根据后台配置的计划规则,解析计划下发巡检任务给一线人员执行,这个业务逻辑会短时间5分钟内下发几千条任务。每一条任务涉及的IO会很多,可能十几次?

  1. 整点下发任务
  2. 整点03分更新任务状态

首先排查是否任务下发导致的CPU升高。但是很快通过SQL统计每个时间段的下发任务数量对比,可以排除这个问题。任务大多数是凌晨0点下发。早上9点-11点下发的任务少数。所以不太可能是任务下发导致CPU升高。再查看凌晨0点,MySQL CPU只有18%左右,相差甚远。

那么继续排查另一个方向:任务的状态修改Job。结合整点03分DB的CPU飙高,推测taskStatusUpdate定时任务导致的概率大。这个任务共有3部分。

从数据量上看,任务关闭和任务预警的数据量都比较少。不太可能是瓶颈。任务开启的数据量较多,概率比较大。着重看下任务开启的方法。

首先是一个没有索引的全表扫表。看日志这个SQL大概1~2s左右。从“开启任务数量”的日志,到“开启任务成功”的日志间隔大概25s左右。佐证这个方法耗时比较慢,可能导致DB CPU飙高。方法里面涉及到IO的以下方法。

各位读者看到下面的IO查询,可以根据给出的信息推理下哪一个是根因导致CPU升高?亦或是组合原因引起的? 下文会给出每一步的耗时日志证明本次的优化的确是优化到问题根因上了。一开始我认为是组合原因引起的,由于a表数据最大1000w以上,且二级索引的区分度比较低0.13左右,结合下面的接近700w的表两次IO更新,如果更新数据量比较大的话是可能导致CPU升高的。

// 1000w数据,workorder_id二级索引区分度13%
List<A> a = aService.list(...);

// 688w数据,主键。这步可省
List<B> bList = bService.listByIds(idList);

// 688w数据,主键
bService.updateBatchById(bList);

// 480w,主键
cService.updateBatchById(cList);

// 186w,task_id二级索引区分度13%
List<D> dList = dService.list(...);

// 网络IO+auth磁盘IO,auth主键,registration_id全表扫描
pushService.push(pushDTO);

但是最后根据打的耗时日志发现居然是最后的pushService.push方法耗时最高且它就是根因,占到整个方法的90%耗时。下图贴出每一步方法的耗时日志可以对应这里的伪代码。

// 1000w数据,workorder_id二级索引区分度13%
// cost 10ms量级
List<A> a = aService.list(...);

// 688w数据,主键。
// 优化后这个查询被省略了 0ms
List<B> bList = bService.listByIds(idList);

// 688w数据,主键
// cost 1~2s量级
bService.updateBatchById(bList);

// 480w,主键
// cost 1s量级
cService.updateBatchById(cList);

// 186w,task_id二级索引区分度13%
// 100ms量级
List<D> dList = dService.list(...);

// 网络IO+auth磁盘IO,auth主键,registration_id全表扫描
// 导致CPU打满的原因,耗时占总体90%
pushService.push(pushDTO);

优化方案

OK,提前破案了,把原因告诉大家了。我按照以下方法慢慢定位出pushService慢的原因。

  • 每个步骤打cost日志
  • 每个IO按需查询
  • A表优化索引,避免回表
  • 节省不必要的IO查询
  • 优化registration_id查询SQL,避免全表扫描

但是为什么pushService的推送会引起CPU的打满?这是一个给用户推送app push的方法,正常情况下不会和DB CPU产生联想。

这里面其实就有一个比较隐蔽的慢查询场景,其实我总结身边80%的数据库CPU打满都和慢SQL有关。因为慢SQL会对表进行大量扫描,通常会将数据页读到Buffer Pool中然后进行大量内存读写和计算,有可能一条慢SQL要遍历几十万~几百万的数据行才能找到目标行。这个过程会大量消耗CPU时间,如果短时间这种慢SQL并发达到一定阈值,MySQL的链接数和CPU就都会被消耗完。

回到pushService排查,里面有一个对user表的查询,需要根据registration_id查出本次app push的目标用户,registration_id是没索引的。而这张表数据并不大只有25w的数据量。找DBA要了CPU打满时间段的慢SQL日志,查找果然这条SQL在其中,并且统计数量在1分钟内有几百条查询,每一条查询也消耗了3~4秒时间,检索22万行数据最终返回32行给客户端。

临时解决方案是给registration_id字段加普通索引,由于表数据量不大且MySQL版本5.7+,DDL是在线替换的,锁表时间很短,期间不阻塞DML语句,直接加索引。

结果回顾

加完索引后,观察下一次任务状态变更Job,MySQL服务器的CPU明显降下来了,从100%降到30~40%,并且持续时间较短。上面提到的加索引是临时解决方案,简单粗暴但有效。但是仍有优化空间,对循环调用查user表可以加缓存或者该批量查询。但是任务变更Job导致的cpu 100%下来后,就凸显了另一个Job的尖刺40~50%左右。

总结

全表扫描的SQL对DB的cpu影响比较高,如果偶发的并不多的请求数量,在监控层面看不出来影响,且单条SQL执行也很快。但是并发多了之后,短时间堆积的慢SQL就会明显占用DB资源。

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

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

相关文章

【Kubernetes】常见面试题汇总(五十一)

目录 114. K8S 集群服务访问失败&#xff08;情况一&#xff09;&#xff1f; 115. K8S 集群服务访问失败&#xff08;情况二&#xff09;&#xff1f; 特别说明&#xff1a; 题目 1-68 属于【Kubernetes】的常规概念题&#xff0c;即 “ 汇总&#xff08;一&#xff…

严重 Zimbra RCE 漏洞遭大规模利用(CVE-2024-45519)

攻击者正在积极利用 CVE-2024-45519&#xff0c;这是一个严重的 Zimbra 漏洞&#xff0c;该漏洞允许他们在易受攻击的安装上执行任意命令。 Proofpoint 的威胁研究人员表示&#xff0c;攻击始于 9 月 28 日&#xff0c;几周前&#xff0c;Zimbra 开发人员发布了针对 CVE-2024-…

TCP/UDP初识

TCP是面向连接的、可靠的、基于字节流的传输层协议。 面向连接&#xff1a;一定是一对一连接&#xff0c;不能像 UDP 协议可以一个主机同时向多个主机发送消息 可靠的&#xff1a;无论的网络链路中出现了怎样的链路变化&#xff0c;TCP 都可以保证一个报文一定能够到达接收端…

Java项目实战II基于Java+Spring Boot+MySQL的甘肃非物质文化网站设计与实现(源码+数据库+文档)

目录 一、前言 二、技术介绍 三、系统实现 四、文档参考 五、核心代码 六、源码获取 全栈码农以及毕业设计实战开发&#xff0c;CSDN平台Java领域新星创作者 一、前言 甘肃省作为中国历史文化名省&#xff0c;拥有丰富的非物质文化遗产资源&#xff0c;涵盖表演艺术、手…

计算机网络期末复习真题(附真题答案)

前言&#xff1a; 本文是笔者在大三学习计网时整理的笔记&#xff0c;哈理工的期末试题范围基本就在此范畴内&#xff0c;就算真题有所更改&#xff0c;也仅为很基础的更改数值&#xff0c;大多跑不出这些题&#xff0c;本文包含简答和计算等大题&#xff0c;简答的内容也可能…

基于SSM的宿舍管理系统 (源码+定制+文档)

博主介绍&#xff1a; ✌我是阿龙&#xff0c;一名专注于Java技术领域的程序员&#xff0c;全网拥有10W粉丝。作为CSDN特邀作者、博客专家、新星计划导师&#xff0c;我在计算机毕业设计开发方面积累了丰富的经验。同时&#xff0c;我也是掘金、华为云、阿里云、InfoQ等平台…

华硕天选笔记本外接音箱没有声音

系列文章目录 文章目录 系列文章目录一.前言二.解决方法第一种方法第二种方法 一.前言 华硕天选笔记本外接音箱没有声音&#xff0c;在插上外接音箱时&#xff0c;系统会自动弹出下图窗口 二.解决方法 第一种方法 在我的电脑上选择 Headphone Speaker Out Headset 这三个选项…

VSCode python代码颜色调整与pycharm对齐

今天开始用VSCode写代码了&#xff0c;因为用服务器比较方便&#xff0c;可是进去一看&#xff0c;代码花花绿绿地完全看不进去&#xff0c;以前用Pycharm的时候就完全没有这种问题&#xff0c;看看人家的颜色格式&#xff01;&#xff08;当然也可能是先入为主&#xff09; 因…

Android SystemUI组件(09)唤醒亮屏 锁屏处理流程

该系列文章总纲链接&#xff1a;专题分纲目录 Android SystemUI组件 本章关键点总结 & 说明&#xff1a; 说明&#xff1a;本章节持续迭代之前章节的思维导图&#xff0c;主要关注左侧上方锁屏分析部分 唤醒亮屏 即可。 Power按键的处理逻辑最终是由PhoneWindowManager来…

Leecode刷题之路第六天之Z字形变换

题目出处 06-Z字形变换 题目描述 个人解法 思路&#xff1a; todo 代码示例&#xff1a;&#xff08;Java&#xff09; todo复杂度分析 todo 官方解法 06-Z字形变换官方解法 方法1&#xff1a;利用二维矩阵模拟 思路&#xff1a; 代码示例&#xff1a;&#xff08;Java&am…

Microsoft 更新 Copilot AI,未來將能使用語音並看到你瀏覽的網頁

不過受到 Recall 事件的影響&#xff0c;更新的推出將更緩慢謹慎。 Microsoft 也同步對其網頁版及行動版的 Copilot AI 進行大改版。這主要是為網頁版換上了一個較為簡單乾淨的介面&#xff0c;並增加了一些新的功能&#xff0c;像是 Copilot Voice 能讓你與 AI 助手進行對話式…

Ansible Playbook原理与实践(Principles and Practice of Ansible Playbook)

&#x1f49d;&#x1f49d;&#x1f49d;欢迎来到我的博客&#xff0c;很高兴能够在这里和您见面&#xff01;希望您在这里可以感受到一份轻松愉快的氛围&#xff0c;不仅可以获得有趣的内容和知识&#xff0c;也可以畅所欲言、分享您的想法和见解。 本人主要分享计算机核心技…

环绕航线规划软件,适配大疆御3e、M300/350适用大疆机型: 经纬M300 rtk、M350rtk、御3e等行业机,能支持kml,㎞z导入。

环绕航线规划软件,适配大疆御3e、M300/350 适用大疆机型: 经纬M300 rtk、M350rtk、御3e等行业机,能支持kml,㎞z导入。 环绕航线规划软件介绍 名称 环绕航线规划软件 (Orbit Flight Planning Software) 适用机型 大疆经纬 M300 RTK大疆经纬 M350 RTK大疆御 3E 行业机功能特…

【技术详解】SpringMVC框架全面解析:从入门到精通(SpringMVC)

文章目录 【技术详解】SpringMVC框架全面解析&#xff1a;从入门到精通(SpringMVC)SpringMVC概述1. 三层架构与MVC架构区别1.1 三层架构1.2 MVC架构1.3前后端分离开发模式 2. SpringMVC环境搭建2.1 注解启动方式2.2 xml启动方式2.3 SpringMVC PostMan工具使用 3. SpringMVC 请求…

electron出现乱码和使用cmd出现乱码

第一种出现乱码。这种可以通过chcp 65001&#xff0c;设置为utf-8的编码。第二种&#xff0c;是执行exec的时候出现乱码&#xff0c;这个时候需要设置一些编码格式&#xff0c;可以通过iconv-lite进行解决&#xff0c;这个方法是node自带的&#xff0c;所以不需要导入。使用方法…

scrapy爬取汽车、车评数据【上】

这个爬虫我想分三期来写&#xff1a; ✅ 第一期写如何爬取汽车的车型信息&#xff1b; ✅ 第二期写如何爬取汽车的车评&#xff1b; ✅ 第三期写如何对车评嵌入情感分析结果&#xff0c;以及用简单的方法把数据插入mysql中&#xff1b; 技术基于scrapy框架、BERT语言模型、mysq…

【springboot】整合沙箱支付

目录 1. 配置沙箱应用环境2. 配置springboot项目1. 引入依赖2. 配置文件注册下载ngrok 3. 创建支付宝支付服务类4. 支付界面模板5. 控制类实现支付6. 测试 1. 配置沙箱应用环境 使用支付宝账号登录到开放平台控制台。 使用支付宝登录后&#xff0c;看到以下页面&#xff0c;下…

2、.Net 前端框架:OpenAuth.Net - .Net宣传系列文章

OpenAuth.Net 是一个开源的身份验证框架&#xff0c;由开发者 Yubaolee 创建&#xff0c;它旨在简化 Web 应用和服务的安全授权过程。这个框架以其强大的功能和易用性&#xff0c;为开发人员提供了一种高效的方式来处理用户认证和授权问题。 OpenAuth.Net 的关键特性包括&#…

无头双向不循环链表的模拟

总共由四部分组成&#xff0c;一个拥有总体方法名参数 的接口、一个异常类、一个方法类、一个测试类 先看我们写入的接口 public interface ILinkList {// 2、无头双向链表实现//头插法void addFirst(int val);//尾插法void addLast(int val);//任意位置插入,第一个数据节点为…