复制到 tmp table 自动增量改变 table
copy to tmp table which alter table on auto increment
我们遇到了 MySql (5.5.x) 的问题,希望您能帮助我们。
在白天的某个时候,我注意到一个状态为“copy to tmp table”的进程,以及这个查询:
ALTER TABLE `MyTableName` AUTO_INCREMENT=200000001
在此之后,所有其他查询都会获得“等待 table 元数据锁定”,并且所有查询都会冻结,并且不会进行任何处理。
我需要终止该进程,然后重新启动所有查询。
为什么?我该如何解决这个问题?
在 MySQL 5.5 中,像您 运行 这样的 ALTER TABLE 会复制整个 table。 table 越大,花费的时间就越多。特别是如果您的存储速度较慢。
你的 table 尺寸是多少(你可以从 SHOW TABLE STATUS LIKE 'MyTableName'\G
得到这个并查看 data_length + index_length
)?
我刚刚在笔记本电脑上进行了测试。我在MySQL 5.5实例中填充了一个table,直到table的大小约为175MB。 运行 更改 table 以设置 auto-increment 值大约需要 5-6 秒。您的结果可能会有所不同,具体取决于您的服务器的功率和存储速度。
虽然 alter table 是 运行ning,但执行该操作的线程在 table 上持有一个 metadata lock,它会阻止所有其他查询,甚至 read-only SELECT 个语句。
ALTER TABLE 作为 MySQL 5.6 的一项功能在 2013 年得到改进。一些类型的改变被优化为完成“in-place”,因此如果没有必要,他们不必复制整个 table。更改 AUTO_INCREMENT 是这些操作之一。不管 table 有多大,如果你改变 table 来改变 AUTO_INCREMENT,它很快,因为它只改变 table 的一个属性,而不需要复制任何行数据。
见https://dev.mysql.com/doc/refman/5.6/en/innodb-online-ddl-operations.html
在MySQL 5.5 中,这些优化没有实现。所以 any alter table 需要很长时间,与 table.
的大小成正比
对于您的情况,我建议解决此问题的最佳方法是升级到较新的版本。 MySQL 5.5 超出其 end-of-life。甚至 MySQL 5.6 也将在 2021 年 2 月达到 end-of-life。是时候升级了。
如果无法升级,则应调查是哪个客户端在执行此 ALTER TABLE 语句。你说你在白天的某个时候注意到了它。追踪下来。在进程列表中,它会告诉您客户端主机 SQL 语句来自 运行。它还会告诉您他们登录的 MySQL 用户。您可能还需要搜索使用此数据库的任何应用程序或脚本的源代码。或者问问你的队友。
一旦找到正在执行此 ALTER TABLE 的客户端,请尝试将客户端 运行 执行此语句的时间更改为 ALTER TABLE不会阻止重要查询。或者询问负责的开发人员是否真的有必要如此频繁地更改 table?
问题可能是由于 服务器重新启动,因为 InnoDb 将最后一个 auto-increment 索引存储在内存中 和 在服务器重新启动时重新计算它 (InnoDB AUTO_INCREMENT Counter Initialization):
If you specify an AUTO_INCREMENT column for an InnoDB table, the table handle in the InnoDB data dictionary contains a special counter called the auto-increment counter that is used in assigning new values for the column. This counter is stored only in main memory, not on disk.
To initialize an auto-increment counter after a server restart, InnoDB executes the equivalent of the following statement on the first insert into a table containing an AUTO_INCREMENT column.
SELECT MAX(ai_col) FROM table_name FOR UPDATE;
InnoDB increments the value retrieved by the statement and assigns it to the column and to the auto-increment counter for the table. By default, the value is incremented by 1. This default can be overridden by the auto_increment_increment configuration setting.
If the table is empty, InnoDB uses the value 1. This default can be overridden by the auto_increment_offset configuration setting.
查看 mysql 日志并尝试找出服务器是否正在重新启动,导致 ALTER table 重置自动增量计数器。
尝试重新启动 mysql 服务器以查看是否出现此行为。
如果是这种情况,您可以尝试:
- 防止重启mysql服务器,可能有cron进程每天重启一次
- 将您的 mysql 版本升级到 8 (Autoicrement saved to table metadata):
In MySQL 8.0, this behavior is changed. The current maximum auto-increment counter value is written to the redo log each time it changes and is saved to an engine-private system table on each checkpoint.
On a server restart following a normal shutdown, InnoDB initializes the in-memory auto-increment counter using the current maximum auto-increment value stored in the data dictionary system table.
- 您可以尝试加快“复制到 tmp table”操作,skip copying to tmp table on disk mysql
参考资料
How to make InnoDB table not reset autoincrement on server restart?
https://serverfault.com/questions/228690/mysql-auto-increment-fields-resets-by-itself
我们遇到了 MySql (5.5.x) 的问题,希望您能帮助我们。 在白天的某个时候,我注意到一个状态为“copy to tmp table”的进程,以及这个查询:
ALTER TABLE `MyTableName` AUTO_INCREMENT=200000001
在此之后,所有其他查询都会获得“等待 table 元数据锁定”,并且所有查询都会冻结,并且不会进行任何处理。
我需要终止该进程,然后重新启动所有查询。
为什么?我该如何解决这个问题?
在 MySQL 5.5 中,像您 运行 这样的 ALTER TABLE 会复制整个 table。 table 越大,花费的时间就越多。特别是如果您的存储速度较慢。
你的 table 尺寸是多少(你可以从 SHOW TABLE STATUS LIKE 'MyTableName'\G
得到这个并查看 data_length + index_length
)?
我刚刚在笔记本电脑上进行了测试。我在MySQL 5.5实例中填充了一个table,直到table的大小约为175MB。 运行 更改 table 以设置 auto-increment 值大约需要 5-6 秒。您的结果可能会有所不同,具体取决于您的服务器的功率和存储速度。
虽然 alter table 是 运行ning,但执行该操作的线程在 table 上持有一个 metadata lock,它会阻止所有其他查询,甚至 read-only SELECT 个语句。
ALTER TABLE 作为 MySQL 5.6 的一项功能在 2013 年得到改进。一些类型的改变被优化为完成“in-place”,因此如果没有必要,他们不必复制整个 table。更改 AUTO_INCREMENT 是这些操作之一。不管 table 有多大,如果你改变 table 来改变 AUTO_INCREMENT,它很快,因为它只改变 table 的一个属性,而不需要复制任何行数据。
见https://dev.mysql.com/doc/refman/5.6/en/innodb-online-ddl-operations.html
在MySQL 5.5 中,这些优化没有实现。所以 any alter table 需要很长时间,与 table.
的大小成正比对于您的情况,我建议解决此问题的最佳方法是升级到较新的版本。 MySQL 5.5 超出其 end-of-life。甚至 MySQL 5.6 也将在 2021 年 2 月达到 end-of-life。是时候升级了。
如果无法升级,则应调查是哪个客户端在执行此 ALTER TABLE 语句。你说你在白天的某个时候注意到了它。追踪下来。在进程列表中,它会告诉您客户端主机 SQL 语句来自 运行。它还会告诉您他们登录的 MySQL 用户。您可能还需要搜索使用此数据库的任何应用程序或脚本的源代码。或者问问你的队友。
一旦找到正在执行此 ALTER TABLE 的客户端,请尝试将客户端 运行 执行此语句的时间更改为 ALTER TABLE不会阻止重要查询。或者询问负责的开发人员是否真的有必要如此频繁地更改 table?
问题可能是由于 服务器重新启动,因为 InnoDb 将最后一个 auto-increment 索引存储在内存中 和 在服务器重新启动时重新计算它 (InnoDB AUTO_INCREMENT Counter Initialization):
If you specify an AUTO_INCREMENT column for an InnoDB table, the table handle in the InnoDB data dictionary contains a special counter called the auto-increment counter that is used in assigning new values for the column. This counter is stored only in main memory, not on disk.
To initialize an auto-increment counter after a server restart, InnoDB executes the equivalent of the following statement on the first insert into a table containing an AUTO_INCREMENT column.
SELECT MAX(ai_col) FROM table_name FOR UPDATE;
InnoDB increments the value retrieved by the statement and assigns it to the column and to the auto-increment counter for the table. By default, the value is incremented by 1. This default can be overridden by the auto_increment_increment configuration setting.
If the table is empty, InnoDB uses the value 1. This default can be overridden by the auto_increment_offset configuration setting.
查看 mysql 日志并尝试找出服务器是否正在重新启动,导致 ALTER table 重置自动增量计数器。
尝试重新启动 mysql 服务器以查看是否出现此行为。
如果是这种情况,您可以尝试:
- 防止重启mysql服务器,可能有cron进程每天重启一次
- 将您的 mysql 版本升级到 8 (Autoicrement saved to table metadata):
In MySQL 8.0, this behavior is changed. The current maximum auto-increment counter value is written to the redo log each time it changes and is saved to an engine-private system table on each checkpoint. On a server restart following a normal shutdown, InnoDB initializes the in-memory auto-increment counter using the current maximum auto-increment value stored in the data dictionary system table.
- 您可以尝试加快“复制到 tmp table”操作,skip copying to tmp table on disk mysql
参考资料
How to make InnoDB table not reset autoincrement on server restart?
https://serverfault.com/questions/228690/mysql-auto-increment-fields-resets-by-itself