CHECK TABLE tbl_name [, tbl_name] ... [option] ...
option: {
FOR UPGRADE
| QUICK
| FAST
| MEDIUM
| EXTENDED
| CHANGED
}
CHECK TABLE
检查一个或多个表是否存在错误。 CHECK TABLE
还可以检查视图是否存在问题,例如视图定义中引用的表是否已不存在。
要检查表,您必须对其具有一定的权限。
CHECK TABLE
适用于 InnoDB
、MyISAM
、ARCHIVE
和 CSV
表。
在对 InnoDB
表运行 CHECK TABLE
之前,请参阅 InnoDB 表的 CHECK TABLE 使用说明。
对于分区表,支持 CHECK TABLE
,并且可以使用 ALTER TABLE ... CHECK PARTITION
来检查一个或多个分区;有关更多信息,请参阅 第 15.1.9 节“ALTER TABLE 语句” 和 第 26.3.4 节“分区的维护”。
CHECK TABLE
会忽略未编入索引的虚拟生成列。
CHECK TABLE
返回一个结果集,其中包含下表所示的列。
列 | 值 |
---|---|
表 |
表名 |
操作 |
始终为 check |
消息类型 |
status 、error 、info 、note 或 warning |
消息文本 |
一条信息性消息 |
该语句可能会为每个已检查的表生成多行信息。最后一行包含 Msg_type
值 status
,并且 Msg_text
通常应为 OK
。表已更新
表示表的存储引擎指示无需检查表。
FOR UPGRADE
选项检查命名的表是否与当前版本的 MySQL 兼容。使用 FOR UPGRADE
时,服务器会检查每个表,以确定自创建表以来,任何表的数据类型或索引是否发生任何不兼容的更改。如果没有,则检查成功。否则,如果可能存在不兼容性,服务器将对表运行完整检查(这可能需要一些时间)。
可能会出现不兼容性,因为数据类型的存储格式已更改,或者其排序顺序已更改。我们的目标是避免这些更改,但偶尔需要进行这些更改,以纠正比版本之间不兼容更糟糕的问题。
FOR UPGRADE
会发现以下不兼容性
在 MySQL 4.1 和 5.0 之间,
InnoDB
和MyISAM
表的TEXT
列中尾部空格的索引顺序已更改。在 MySQL 5.0.3 和 5.0.5 之间,新的
DECIMAL
数据类型的存储方法已更改。有时会对字符集或排序规则进行更改,这需要重建表索引。有关此类更改的详细信息,请参阅 第 3.5 节“MySQL 8.4 中的更改”。有关重建表的更多信息,请参阅 第 3.14 节“重建或修复表或索引”。
MySQL 8.4 不支持旧版 MySQL 中允许的两位数
YEAR(2)
数据类型。对于包含YEAR(2)
列的表,CHECK TABLE
建议使用REPAIR TABLE
,这会将两位数的YEAR(2)
列转换为四位数的YEAR
列。会保留触发器的创建时间。
如果表包含 5.6.4 之前版本的旧时间类型列(
TIME
、DATETIME
和TIMESTAMP
列不支持小数秒精度),则会将其报告为需要重建。这有助于 MySQL 升级过程检测和升级包含旧时间类型列的表。会针对使用非原生分区的表发出警告,因为 MySQL 8.4 中删除了非原生分区。请参阅 第 26 章“分区”。
下表显示了可以提供的其他检查选项。这些选项将传递给存储引擎,存储引擎可以使用或忽略它们。
类型 | 含义 |
---|---|
QUICK |
不扫描行以检查链接是否错误。适用于 InnoDB 和 MyISAM 表和视图。 |
FAST |
仅检查未正确关闭的表。对于 InnoDB 而言,将被忽略;仅适用于 MyISAM 表和视图。 |
CHANGED |
仅检查自上次检查后已更改或未正确关闭的表。对于 InnoDB 而言,将被忽略;仅适用于 MyISAM 表和视图。 |
MEDIUM |
扫描行以验证删除的链接是否有效。这还会计算行的键校验和,并使用计算出的键校验和对其进行验证。对于 InnoDB 而言,将被忽略;仅适用于 MyISAM 表和视图。 |
EXTENDED |
对每一行的所有键执行完整的键查找。这可确保表 100% 一致,但需要很长时间。对于 InnoDB 而言,将被忽略;仅适用于 MyISAM 表和视图。 |
您可以组合检查选项,如下面的示例所示,该示例对表执行快速检查以确定其是否已正确关闭
CHECK TABLE test_table FAST QUICK;
如果 CHECK TABLE
在标记为““已损坏”” 或““未正确关闭”” 的表中未发现问题,则 CHECK TABLE
可能会删除该标记。
如果表已损坏,则问题很可能出在索引中,而不是数据部分中。上述所有检查类型都会彻底检查索引,因此应该可以发现大多数错误。
要检查您认为没有问题的表,请不要使用检查选项或使用 QUICK
选项。当您赶时间并且可以承担 QUICK
在数据文件中找不到错误的极小风险时,应使用后者。(在大多数情况下,在正常使用情况下,MySQL 应该能够发现数据文件中的任何错误。如果发生这种情况,该表将被标记为““已损坏””,并且在修复之前无法使用。)
FAST
和 CHANGED
主要用于从脚本(例如,从 cron 执行)定期检查表。在大多数情况下,FAST
比 CHANGED
更可取。(唯一不可取的情况是,当您怀疑在 MyISAM
代码中发现了一个错误时。)
EXTENDED
仅在您运行了正常检查但在 MySQL 尝试更新行或按键查找行时仍然从表中获取错误后使用。如果正常检查已成功,则不太可能出现这种情况。
使用 CHECK TABLE ... EXTENDED
可能会影响查询优化器生成的执行计划。
CHECK TABLE
报告的某些问题无法自动更正
找到 auto_increment 列值为 0 的行
.这意味着表中有一行的
AUTO_INCREMENT
索引列包含值 0。(可以通过使用UPDATE
语句将列显式设置为 0 来创建AUTO_INCREMENT
列为 0 的行。)这本身并不是错误,但如果您决定转储表并还原它或对表执行
ALTER TABLE
,则可能会导致问题。在这种情况下,AUTO_INCREMENT
列会根据AUTO_INCREMENT
列的规则更改值,这可能会导致重复键错误等问题。要消除警告,请执行
UPDATE
语句以将该列设置为除 0 以外的某个值。
以下说明适用于 InnoDB
表
如果
CHECK TABLE
遇到损坏的页面,则服务器将退出以防止错误传播(错误 #10132)。如果损坏发生在辅助索引中,但表数据可读,则运行CHECK TABLE
仍可能导致服务器退出。如果
CHECK TABLE
在聚集索引中遇到损坏的DB_TRX_ID
或DB_ROLL_PTR
字段,则CHECK TABLE
可能会导致InnoDB
访问无效的撤消日志记录,从而导致与 MVCC 相关的服务器退出。如果
CHECK TABLE
在InnoDB
表或索引中遇到错误,它将报告错误,并且通常会将索引标记为已损坏,有时还会将表标记为已损坏,从而阻止进一步使用索引或表。此类错误包括辅助索引中的条目数量错误或链接错误。如果
CHECK TABLE
在辅助索引中发现条目数量错误,它将报告错误,但不会导致服务器退出或阻止访问文件。CHECK TABLE
会检查索引页结构,然后检查每个键条目。它不会验证指向聚集记录的键指针,也不会遵循BLOB
指针的路径。当
InnoDB
表存储在其自己的.ibd
文件 中时,.ibd
文件的前 3 个 页面 包含标头信息,而不是表或索引数据。CHECK TABLE
语句不会检测仅影响标头数据的不一致。要验证InnoDB
.ibd
文件的全部内容,请使用 innochecksum 命令。在大型
InnoDB
表上运行CHECK TABLE
时,其他线程可能会在CHECK TABLE
执行期间被阻塞。为了避免超时,信号量等待阈值(600 秒)为CHECK TABLE
操作延长了 2 小时(7200 秒)。如果InnoDB
检测到信号量等待时间为 240 秒或更长,它会开始将InnoDB
监视器输出打印到错误日志。如果锁请求超过了信号量等待阈值,InnoDB
将中止该进程。要完全避免出现信号量等待超时的可能性,请运行CHECK TABLE QUICK
而不是CHECK TABLE
。InnoDB
SPATIAL
索引的CHECK TABLE
功能包括 R 树有效性检查以及确保 R 树行计数与聚簇索引匹配的检查。CHECK TABLE
支持虚拟生成列上的二级索引,这些索引受InnoDB
支持。InnoDB
支持并行聚簇索引读取,这可以提高CHECK TABLE
的性能。InnoDB
在CHECK TABLE
操作期间读取聚簇索引两次。第二次读取可以并行执行。必须将innodb_parallel_read_threads
会话变量设置为大于 1 的值才能进行并行聚簇索引读取。用于执行并行聚簇索引读取的实际线程数由innodb_parallel_read_threads
设置或要扫描的索引子树数决定,取较小者。
以下说明适用于 MyISAM
表
CHECK TABLE
更新MyISAM
表的关键统计信息。如果
CHECK TABLE
输出没有返回OK
或表已经是最新状态
,则通常应该运行表修复。请参阅第 9.6 节“MyISAM 表维护和崩溃恢复”。如果没有指定任何
CHECK TABLE
选项QUICK
、MEDIUM
或EXTENDED
,则动态格式MyISAM
表的默认检查类型为MEDIUM
。这与在表上运行 myisamchk --medium-checktbl_name
的结果相同。对于静态格式的MyISAM
表,默认检查类型也是MEDIUM
,除非指定了CHANGED
或FAST
。在这种情况下,默认值为QUICK
。对于CHANGED
和FAST
,将跳过行扫描,因为行很少损坏。