我看到了一些专用的MySQL服务器,它们从未使用过多个内核。我比DBA for MySQL更开发人员,因此需要一些帮助。

设置

这些服务器非常笨重,并带有OLAP / DataWarehouse(DW)类型负载:


主要:96GB RAM,8核+单个RAID 10阵列
测试:32GB RAM,4核
最大的DB为540 GB,总容量约为1.1TB,大部分InnoDB表
Solaris 10 Intel-64
MySQL 5.5.x

注意:最大的数据库是从OLTP DR服务器复制的数据库,并且从中装载了DW。它不是完整的DW:仅持续6个月到6周,因此它比OLTP数据库小。

测试服务器上的观察结果


3单独的连接
每个都有一个并发(和不同的)ALTER TABLE...DROP KEY...ADD INDEX

3个表有2.5、3.8和450万行
CPU使用率高达25%(一个核心上限)且没有更高的值
3个ALTER需要12-25分钟(最小的一个需要4.5分钟)

问题


什么设置或使用补丁程序才能使用多个内核?
,为什么MySQL不使用所有可用内核? (像其他RDBMS一样)
是复制的结果吗?

其他说明


我了解RDBMS“线程”和“ RDBMS”之间的区别操作系统“线程”
我没有问任何形式的并行性
InnoDB的一些系统变量和线程不是最优的(寻找快速的胜利)如果需要,可以调整操作系统
最小表上的单个ALTER TABLE需要4.5分钟(使IMO震惊)

编辑1


innodb_thread_concurrency都设置为8。是的,这是错误的,但不会使MySQL使用多个内核。
innodb_buffer_pool_size在主数据库上为80GB,在测试中为10GB(另一个实例已关闭)。暂时可以。
innodb_file_per_table = ON

编辑2


innodb_flush_log_at_trx_commit = 2
innodb_use_sys_malloc = ON

要测试


innodb_flush_method何时应显示为O_DIRECT
将遵循RolandoMySQLDBA的设置

让我知道我是否错过了任何重要事项

干杯

更新


在RolandoMySQLDBA的答案中更改了innodb_flush_method + 3个线程设置
结果:>用于测试的1个核心=阳性结果

评论

这个问题变得过时了-新版本的ALTER现在可以更快地添加/删除索引。进一步请注意,问题是询问是否要在受I / O约束的进程中投入更多的内核,这无济于事。

#1 楼

我实际上是在2011年5月的Percona Live NYC会议上与MySQL专家讨论过innodb_thread_concurrency的。 。这样,InnoDB会为给定的MySQL实例设置确定打开innodb_thread_concurrency的最佳数量。

innodb_concurrency_tickets设置为0后,就可以将innodb_thread_concurrencyinnodb_read_io_threads(均从MySQL 5.1.38开始)设置为最大值为64。这应该使用更多的内核。

评论


没有冒犯,但是对于MySQL 8和8年后的情况,关于InnoDB性能的几乎所有问题和答案都不再适用吗?

– Peter VARGA
19年3月3日在22:10

@AlBundy没有冒犯,但是请记住,仍在使用MySQL 5.5的人数和公司的数量惊人(该版本于2018年12月停产)。因此,只要积极使用5.5,发布用于调优5.5的答案仍然有价值。

– RolandoMySQLDBA
19 Mar 4 '19 at 14:05

当然,但是我的意思是明确地对于MySQL 8而言,这些帖子并不适用。

– Peter VARGA
19 Mar 4 '19 at 14:07

#2 楼

MySQL将自动使用多个内核,因此25%的负载是巧合1或在Solaris上潜在的配置错误。我不会假装不知道如何调整solaris,但是这里有一篇文章介绍了一些solaris特定的调整信息。

在MySQL 5.5中对InnoDB调整页面进行了全面检查,因此有还有一些很好的信息。来自InnoDB磁盘IO提示:


如果Unix顶级工具或Windows任务管理器显示您的工作负载中的CPU使用率小于70%,则您的工作负载可能是磁盘-界。也许您提交的事务过多,或者缓冲池太小。增大缓冲池可能会有所帮助,但不要将其设置为等于物理内存的80%以上。


还要检查其他一些事情: br />将innodb_flush_method切换为O_DIRECT值得测试。如果这有帮助,您可能需要使用forcedirectio选项安装文件系统
将innodb_flush_log_at_trx_commit从1更改为0(如果您不介意在mysql崩溃时丢失最后一秒)或2(如果您不介意丢失)操作系统崩溃的最后一秒)。

检查innodb_use_sys_malloc的值。本文提供了有关该变量的更多信息。


那时,还没有针对多核CPU调整的内存分配器库。因此,InnoDB在mem子系统中实现了自己的内存分配器。此分配器由单个互斥体保护,这可能会成为瓶颈。在5.5中默认启用)。


请注意,当禁用InnoDB内存分配器时,InnoDB将忽略参数innodb_additional_mem_pool_size的值。



复制可能会导致某些问题。我意识到您对并行性不感兴趣,但是从此工作日志的描述中可以看出:


当前,复制在多核计算机上无法很好地扩展。
单个从属线程一个接一个地执行复制事件,并且可能无法解决
由并发多个客户端连接产生的负载
/>最终,由于发生基于磁盘的操作,因此InnoDB可能不是最佳的数据仓库引擎。您可以考虑更改要压缩的MyISAM数据仓库表。

1巧合的是,我的意思是存在一个瓶颈,可以防止您的负载增加到25%以上,但不一定是强制单核心问题。

评论


现在,复制(可选)在从属服务器上是多线程的。自编写此答案以来,InnoDB已得到改进。我不建议您使用MyISAM,尤其是如果没有压缩的话。

–里克·詹姆斯(Rick James)
19年1月15日在18:39

#3 楼

注意:此答案是关于使用多个内核的单个连接。 OP的问题不明确;它错误地认为MySQL整体上不能使用多个内核。其他答案正确指出3-Alter测试用例确实是I / O绑定的,因此无法证明标题问题。

单个连接将仅使用单个内核。 (好吧,InnoDB使用其他线程(因此使用内核)来进行某些I / O处理,但这并不重要。)

您有3个ALTER,所以使用的内核价值不超过3个。

可惜,即使PARTITION也不使用多个内核。

直到最近,在4-8个内核之后,多个连接将达到最大值。 Percona的Xtradb(包含在MariaDB中)更好地利用了多个内核,但每个线程仍然只有一个。它们最多可容纳32个内核。

(2015年更新:) 5.6的多个连接最多可容纳48个内核。 5.7承诺会更好。 (因此,Oracle基准测试说。)但仍然没有为单个连接使用多个内核。

更新(在使用Oracle的OpenWorld之后):新版本8.x将没有任何并行性。 />
进一步更新-8.0.17在某些情况下会在很少的选定查询上使用多个内核。 (也就是说,不要激动。)

#4 楼

恕我直言,在上述用例中,您永远不会使用多个内核。原因是您的工作负载受IO约束,而不受CPU约束。当您的3个连接创建一个新的索引时,每个连接都需要从磁盘读取整个表:这是在花时间,而不是在计算索引。

#5 楼

请考虑您的瓶颈可能是文件系统的IO性能。情况下,将noatime安装到/etc/fstab)。

默认情况下,Linux会记录每个磁盘读取或写入的访问时间,这会对IO性能产生负面影响,尤其是对于数据库等高IO应用程序而言。这意味着即使从文件中读取数据也会触发对磁盘的写操作... WAT! ):

/dev/sdb1  /data01  ext4  defaults,noatime  0  2


然后重新安装分区:使用该分区的应用程序。但是...将所有数据保存在内存中无所不能。