问题
今天做测试遇到一个问题,在服务往DB插入数据时,出现插入失败,发现报1467的错误。
将日志打印的插入SQL到命令行直接执行,同样提示1467错误,并有了更详细的说明:
ERROR 1467 (HY000): Failed to read auto-increment value from storage engine
分析
这个报错看起来是跟自增字段有关。
查资料后了解到,其原因是自增字段的数值已经超过了字段类型能够容纳的范围。
也就是说,自增字段的类型对应一个数值范围,当自增ID增长到一定值的时候,会超出范围,此时就会导致自增ID字段自增失败了。
通过以下语句看一下当前自增ID的类型范围和当前自增ID增长到了多少:
> show create table T_XX;
CREATE TABLE `T_XX` (
`FId` bigint(11) unsigned NOT NULL AUTO_INCREMENT COMMENT '自增主键',
……
) ENGINE=InnoDB AUTO_INCREMENT=18446744073 DEFAULT CHARSET=utf8
可见当前的自增逐渐的范围是11位无符号整型,而最后的AUTO_INCREMENT的值其实就是记录当前表中最大的自增主键的值是多少,可以看到已经达到了11位,无法继续增加,才会报错。
了解原因后,就可以对症下药。
解决
这里可以有两个思路:
- 如果ID是正常增长到极限,此时需要调大自增ID的范围
- 如果ID是异常出现了部分新的极大ID,导致无法继续增长,此时可以删去异常记录,调整表的自增ID游标。
思路1
有可能随着测试操作,ID就是增长到了极限,此时不好删数据,只能调大自增ID的范围。
可以通过以下语句来修改自增逐渐的类型范围:
ALTER TABLE T_XX MODIFY `FId` bigint(20) UNSIGNED NOT NULL AUTO_INCREMENT COMMENT '自增主键';
此时再查看建表语句就会发现自增ID的范围已经增大了:
> show create table T_XX;
CREATE TABLE `T_XX` (
`FId` bigint(20) unsigned NOT NULL AUTO_INCREMENT COMMENT '自增主键',
……
) ENGINE=InnoDB AUTO_INCREMENT=18446744073 DEFAULT CHARSET=utf8
思路2
有时仅仅是因为一些异常情况导致出现几条极大的自增ID值的记录,此时可以删去它们,然后将当前的自增主键游标修改即可。
先查看数据,删去异常的ID的记录。
然后查到正常增长到的ID,假设是12666,执行以下语句:
ALTER TABLE T_XX AUTO_INCREMENT = 12666;
此时再查看建表语句,就会发现已经恢复了游标,可以继续插入了:
> show create table T_XX;
CREATE TABLE `T_XX` (
`FId` bigint(11) unsigned NOT NULL AUTO_INCREMENT COMMENT '自增主键',
……
) ENGINE=InnoDB AUTO_INCREMENT=12666 DEFAULT CHARSET=utf8
关注我的公众号【月亮与二进制】,鹅厂程序员的敲码间隙,也能读书观影练剑写字,分享给你我的世界
网友评论