MySQL Insert语句单个批次数量过多导致的CPU性能问题分析
【问题】
最近有台服务器比较频繁的CPU报警,表现的特征有CPU sys占比偏高,大量慢查询,大量并发线程堆积。后面开发对insert的相关业务限流后,服务器性能恢复正常。
【异常期间线程处理情况】
下图是当时生产环境异常时抓取的信息,该事务正在执行insert,已经执行5秒,线程运行在innodb内核,状态是thread declared inside InnoDB,还有4906 tickets可用
统计了下有64个线程在innodb层,同时看到还有280个线程在排队等待进入innodb线程,状态是sleeping before entering InnoDB
innodb层的并发线程执行的SQL比较慢,产生了阻塞,导致了mysql的并发线程堆积。
【哪些SQL执行慢】
从正在执行的SQL中,看到了insert的慢查询SQL语句,统计了下这句SQL批量插入大于342条记录(SQL被截断)
【批量insert的性能测试】
类似这种批量的insert SQL会对MySQL性能造成影响吗,多大的批次比较合理呢,做了下面测试
在测试服务器上新建测试表(表结构同生产环境),并定义了5个插入脚本,分别为单条insert,每10条1个批次insert,每50条1个批次insert,每100条1个批次insert,每340条1个批次insert
用压测工具模拟512个并发线程的情况下,不同类型的SQL插入100W条记录服务器的性能情况,下表是压测统计
数据量 |
并发线程 |
执行时间(秒) |
每秒insert |
慢查询数量 |
Context switch |
CPU使用率 |
CPU sys占比 |
|
普通insert(1条) |
1000000 |
512 |
33 |
3W |
0 |
79W |
73% |
39% |
批量SQL(10条) |
1000000 |
512 |
23 |
4.3W |
0 |
49W |
78% |
56% |
批量SQL(50条) |
1000000 |
512 |
21 |
4.7W |
0 |
42W |
80% |
60% |
批量SQL(100条) |
1000000 |
512 |
15 |
6.6W |
20 |
53W |
70% |
45% |
批量SQL(340条) |
1000000 |
512 |
15 |
6.6W |
200 |
38W |
86% |
70% |
下图是批量SQL(340条)执行时的性能情况,可以看到当每100条记录一个批次执行insert时,开始出现慢查询,每340条1个批次执行insert时,在高并发的情况下,会产生大量的慢查询,这个现象接近于我们目前生产环境异常时的情况
【优化方案】
对于MySQL需要插入大量数据时,每次单条的insert性能较差,为了提升insert性能,我们采用了每批次多条记录同时insert的方法。
但当批次增大到一定数量时,在高并发访问的情况下,单个批次执行的性能会出现较大的下降,出现大量慢查询,并发线程堆积,CPU上升出现瓶颈, innodb层的并发线程处理被慢查询阻塞,后面只能通过限流来缓解性能问题。
根据上面的测试结论,建议控制热表单个批次insert的记录条数,最好单个批次控制在10条左右(因为即使调大到50条,插入性能没有大的提升,在高并发场景下,首先要保证当前SQL的执行性能)。
【优化后CPU告警消失,运行平稳】
MySQL Insert语句单个批次数量过多导致的CPU性能问题分析的更多相关文章
- 使用 xlrd 模块实现对excel 的读取、excel转json 、excel 转 mysql insert 语句
#-*- coding:utf-8 -*- # 处理 excel 中的 area 为 Mysql insert 语句 import xlrd, json, codecs, os # data = xl ...
- mysql INSERT语句 语法
mysql INSERT语句 语法 作用:用于向表格中插入新的行. 语法:INSERT INTO 表名称 VALUES (值1, 值2,....)或者INSERT INTO table_name (列 ...
- MySQL INSERT语句
insert的语法 INSERT [LOW_PRIORITY | DELAYED | HIGH_PRIORITY] [IGNORE] [INTO] tbl_name [(col_name,...)] ...
- Mysql查询语句使用select.. for update导致的数据库死锁分析
近期有一个业务需求,多台机器需要同时从Mysql一个表里查询数据并做后续业务逻辑,为了防止多台机器同时拿到一样的数据,每台机器需要在获取时锁住获取数据的数据段,保证多台机器不拿到相同的数据. 我们My ...
- MySQL insert语句锁分析
最近对insert的锁操作比较费解,所以自己动手,一看究竟.主要是通过一下三个sql来看一下执行中的sql的到底使用了什么锁. select * from information_schema.INN ...
- Mysql insert语句的优化
1) 如果你同时从同一客户插入很多行,使用多个值表的INSERT语句.这比使用分开INSERT语句快(在一些情况中几倍). Insert into test values(1,2),(1,3), ...
- mysql insert语句错误问题解决
好久没有复习数据库了,竟然忘记了mysql中的关键字(保留字),导致今天一晚上都在查找sql语句错误,特此记录此错误,教训啊. 我在mysql数据库中有一个名为order 的表,啊啊啊啊啊,为啥我给他 ...
- 简例 一次执行多条mysql insert语句
package com.demo.kafka;import java.sql.Connection;import java.sql.DriverManager;import java.sql.Prep ...
- excel 里面拼接 MySQL insert 语句
="('"&A2&"',"&" '"&B2&"','"&C2&& ...
随机推荐
- spring-boot Test for Controller
spring-boot controller 测试示例: 单元测试类 package com.zzhi; import com.fasterxml.jackson.databind.ObjectMa ...
- JS对象中的原型
对象的原型:每个对象都连接一个原型对象,并且它可以从中继承属性.所有通过对象字面量创建的对象都连接到object.prototype.当你创建一个新对象时,你可以选择某个对象作为它的原型.原型连接在更 ...
- C 语言中指针初始化为字符串常量 不可通过该指针修改其内容
char b[] = "hello"; 则“hello”存于栈中,因为定义的是一个数组. char *b = "hello"; 则"hello&quo ...
- Linux 下子进程与父进程的关系
我们知道,Linux下父进程可以使用fork 函数创建子进程,但是当父进程先退出后,子进程会不会也退出呢? 通过下面这个小实验,我们能够很好的看出来: /******** basic.c ****** ...
- 基本控件文档-UIKit结构图
CHENYILONG Blog 基本控件文档-UIKit结构图 Fullscreen UIKit结构图 技术博客http://www.cnblogs.com/ChenYilong/ 新浪微博htt ...
- 【leetcode 简单】 第五十八题 计数质数
统计所有小于非负整数 n 的质数的数量. 示例: 输入: 10 输出: 4 解释: 小于 10 的质数一共有 4 个, 它们是 2, 3, 5, 7 . class Solution: def cou ...
- 网页中嵌入swf文件的几种方法
1. object + embed 传统的方法 优点:浏览器兼容性好,是 Macromedia 一直以来的官方方法缺点:a.embed 标签是不符合 W3C 的规范的,无法通过验证.当然, ...
- 【API】Mysql UDF BackDoor
1.MySQL UDF是什么 UDF是Mysql提供给用户实现自己功能的一个接口,为了使UDF机制起作用,函数必须用C或C ++编写,并且操作系统必须支持动态加载.这篇文章主要介绍UDF开发和利用的方 ...
- 高级C#信使(译) - Unity维基百科
高级C#信使 作者:Ilya Suzdalnitski 译自:http://wiki.unity3d.com/index.php/Advanced_CSharp_Messenger 描述 前言 Mis ...
- mysql高可用架构 -> MHA部署-04
MHA架构图 本次MHA的部署基于GTID复制成功构建,普通主从复制也可以构建MHA架构. 下载所需的软件包 mkdir /server/tools -p //创建存放包的目录 [root@db01 ...