mysql-57中的内部临时表

最近,我在为一个客户调查一个有趣的案例。 我们可以在描述“InnoDB行插入”度量(从1K/秒跳跃到6K/秒)的图表上看到有规律的峰值;然而,我们无法将这些峰值与其他活动联系起来。 这

mysql-57中的内部临时表

其他图形(Com_*,Handler_*)没有显示任何这样的尖峰。 我检查了日志(我们无法启用常规日志或更改慢速日志的阈值)、触发器、存储过程、准备好的语句,甚至查看了二进制日志。 然而,我没有找到任何一个 可能导致插入6K行峰值的查询。

最后,我发现我关mysql数据库同步 注的是错误的查询。 我试图将InnoDB行插入图中的峰值与DML查询(写入)相关联。 然而,峰值是由查询引起的! 但是为什么查询会导致大量的InnoDB插入操作呢? 这怎么可能呢?

事实证明,这与磁盘上的临时表有关。 在MySQL 5中。7的默认设置是为InnoDB设置的。 这意味着如果需要在磁盘上创建一个临时表(即像其他InnoDB表一样,它也有InnoDB的所有限制 for)它将使用InnoDB存储引擎。

很糟糕吗? 不一定。 Krunal Bauskar发表了一篇博文,最初是关于MySQL 5中InnoDB内部表的性能。7. InnoDB内部临时表没有重做/撤消记录。 所以总的来说性能更好。 然而,我们需要注意以下几点:

  1. 更改MySQL存储临时表的位置。 InnoDB临时表存储在表空间文件中。 There are a number of challenges with that:
    • 文件的位置。 默认情况下,它位于。 最初,MyISAM临时表存储在。 我们可以配置文件的大小,但是位置总是相对于InnoDB的,所以要移动到 ,
    • 我们需要这样的东西:。 与其他表空间一样,它从不收缩(尽管在重新启动时会被截断)。 巨大的临时表可以填满磁盘并挂起MySQL (bug打开)。
    • 解决这个问题的一种方法是设置文件的最大大小:。e. e. InnoDB行或列限制。 如果超过这些值,它将返回“行大小太大”或“列太多”的错误。
  2. 解决方法是设置为MYISAM。 当所有临时表都转到InnoDB时,它可能会增加引擎总负载并影响其他查询。 例如,如果最初所有数据集都适合InnoDB,并且临时表是在InnoDB之外创建的,则不会影响Innodb的内存占用。

现在,如果一个巨大的临时表被创建为InnoDB表,它将使用并可能“驱逐”现有的页面,这样其他查询可能执行得更慢。当心MySQL 5中的新变化。 7:内部临时表(那些在需要临时表时为选择而创建的表)存储在InnoDB文件中。 在大多数情况下,这更快。 然而,它可以改变原来的行为。