为什么插入查询偶尔需要很长时间才能完成?

Dan*_*iel 33 mysql sql performance query-cache

这是一个非常简单的问题.将数据插入表中通常可以正常工作,除了插入查询需要几秒钟的几次.(我并不想批量插入数据).所以我设置了插入过程的模拟,找出为什么插入查询偶尔会超过2秒运行.约书亚建议可以调整索引文件; 我删除了id(主键字段),但延迟仍然发生.

我有一个MyISAM表:( daniel_test_insert这个表开始完全为空):

create table if not exists daniel_test_insert ( 
    id int unsigned auto_increment not null, 
    value_str varchar(255) not null default '', 
    value_int int unsigned default 0 not null, 
    primary key (id) 
)
Run Code Online (Sandbox Code Playgroud)

我将数据插入其中,有时插入查询需要> 2秒才能运行. 此表上没有读取 - 只能通过单线程程序串行写入.

我运行完全相同的查询100,000次,以查找查询时间为何需要很长时间.到目前为止,它似乎是随机发生的.

例如,此查询花了4.194秒(插入的时间很长):

Query: INSERT INTO daniel_test_insert SET value_int=12345, value_str='afjdaldjsf aljsdfl ajsdfljadfjalsdj fajd as f' - ran for 4.194 seconds
status               | duration | cpu_user  | cpu_system | context_voluntary | context_involuntary | page_faults_minor
starting             | 0.000042 | 0.000000  | 0.000000   | 0                 | 0                   | 0                
checking permissions | 0.000024 | 0.000000  | 0.000000   | 0                 | 0                   | 0                
Opening tables       | 0.000024 | 0.001000  | 0.000000   | 0                 | 0                   | 0                
System lock          | 0.000022 | 0.000000  | 0.000000   | 0                 | 0                   | 0                
Table lock           | 0.000020 | 0.000000  | 0.000000   | 0                 | 0                   | 0                
init                 | 0.000029 | 0.000000  | 0.000000   | 1                 | 0                   | 0                
update               | 4.067331 | 12.151152 | 5.298194   | 204894            | 18806               | 477995           
end                  | 0.000094 | 0.000000  | 0.000000   | 8                 | 0                   | 0                
query end            | 0.000033 | 0.000000  | 0.000000   | 1                 | 0                   | 0                
freeing items        | 0.000030 | 0.000000  | 0.000000   | 1                 | 0                   | 0                
closing tables       | 0.125736 | 0.278958  | 0.072989   | 4294              | 604                 | 2301             
logging slow query   | 0.000099 | 0.000000  | 0.000000   | 1                 | 0                   | 0                
logging slow query   | 0.000102 | 0.000000  | 0.000000   | 7                 | 0                   | 0                
cleaning up          | 0.000035 | 0.000000  | 0.000000   | 7                 | 0                   | 0
Run Code Online (Sandbox Code Playgroud)

(这是SHOW PROFILE命令的缩写版本,我扔的是,都是零列.)

现在,更新具有令人难以置信的上下文切换次数和次要页面错误.Opened_Tables在这个数据库上每10秒增加大约1个(没有用完table_cache空间)

统计:

  • MySQL 5.0.89

  • 硬件:32 GB的ram/8核@ 2.66GHz; raid 10 SCSI硬盘(SCSI II ???)

  • 我查询了硬盘驱动器和raid控制器:没有报告错误.CPU空闲率约为50%.

  • iostat的-x 5(报告小于10%利用率硬碟)顶部报告负载平均约10 1分钟(正常为我们的分贝机)

  • 交换空间有156k使用(32演出的ram)

我不知道是什么导致这种性能滞后.这不会发生在我们的低负载从站上,只发生在我们的高负载主站上.内存和innodb表也会发生这种情况.有没有人有什么建议?(这是一个生产系统,所以没有异国情调!)

Rie*_*sio 21

我在我的系统上发现了同样的现象.通常需要一毫秒的查询将突然需要1-2秒.我的所有情况都是简单的单表INSERT/UPDATE/REPLACE语句---不在任何SELECT上.没有明显的负载,锁定或螺纹堆积.

我怀疑它是由于清除了脏页,刷新磁盘更改或一些隐藏的互斥锁,但我还没有将其缩小.

也排除了

  • 服务器负载 - 与高负载无关
  • 引擎 - 与InnoDB/MyISAM/Memory一起发生
  • MySQL查询缓存 - 无论是打开还是关闭
  • 记录旋转 - 事件中没有相关性

我在这一点上唯一的另一个观察结果来自我在多台机器上运行相同数据库的事实.我有一个繁重的读取应用程序,所以我使用的是复制环境 - 大部分负载都在奴隶上.我注意到即使主机上的负载很小,这种现象也会发生.即使我没有看到锁定问题,也许它的Innodb/Mysql在(线程)并发方面遇到了麻烦?回想一下,从站的更新将是单线程的.

MySQL Verion 5.1.48

更新

我认为我的问题在我的案件中处于领先地位.在我的一些服务器上,我注意到这种现象比其他服务器更多.看到不同服务器之间有什么不同,并调整周围的事情,我引导了MySQL innodb系统变量 innodb_flush_log_at_trx_commit.

我发现文档读起来有点尴尬,但innodb_flush_log_at_trx_commit可以取1,2,0的值:

  • 对于1,每次提交都会将日志缓冲区刷新到日志文件中,并且每次提交都会将日志文件刷新到磁盘.
  • 对于2,每次提交都会将日志缓冲区刷新到日志文件中,并且大约每1-2秒将日志文件刷新到磁盘.
  • 对于0,日志缓冲区每秒刷新到日志文件,日志文件每秒刷新到磁盘.

实际上,按照报告和记录的顺序(1,2,0),您应该在交易中获得越来越高的风险.

话虽如此,我发现服务器innodb_flush_log_at_trx_commit=0的性能比使用的服务器差得多(即"长更新"的10-100倍)innodb_flush_log_at_trx_commit=2.此外,当我将其切换为2时,在不良实例上的情况会立即得到改善(请注意,您可以动态更改它).

所以,我的问题是,你的目标是什么?请注意,我不是指责此参数,而是强调它的上下文与此问题有关.

  • 一年前,当我的query_cache太大时,我确实遇到了类似的问题,因此当大量数据无效时,整个服务器将锁定最多30秒.请注意:http://dom.as/2009/07/08/query-cache-tuning/ (2认同)