TRUNCATE PARTITION 不能完全避免锁表,但仅对目标分区加 MDL_WRITE 锁,不影响其他分区及 DML;仅支持 RANGE、LIST、COLUMNS 分区,不支持 HASH 和 KEY;需检查分区名大小写、事务占用及 MySQL 版本(8.0.23+ 才支持二级分区)。

TRUNCATE PARTITION 能否真正避免锁表?
不能完全避免,但锁的粒度大幅降低——TRUNCATE PARTITION 只对目标分区加 MDL_WRITE 元数据锁(而非整表 MDL_EXCLUSIVE),其他分区和 DML 操作基本不受影响。前提是:表使用 innodb_file_per_table=ON,且分区是 INNODB 引擎。
哪些分区类型支持 TRUNCATE PARTITION?
仅支持 RANGE、LIST、COLUMNS 分区;HASH 和 KEY 分区不支持该语法,执行会报错:ERROR 1735 (HY000): Unknown partition 'p0' in table 't'(即使分区存在)。可通过 SELECT PARTITION_NAME FROM INFORMATION_SCHEMA.PARTITIONS WHERE TABLE_NAME='t' 确认分区类型。
执行前必须检查的三项配置
-
SQL_LOG_BIN=OFF不是必须项,但若在主库执行且 binlog_format=ROW,TRUNCATE PARTITION会被记录为单条事件,从库回放时仍走分区级清空逻辑——这点比DELETE更安全 - 确认分区名拼写严格匹配(区分大小写,取决于
lower_case_table_names设置),错误示例:TRUNCATE PARTITION p202401实际分区名为P202401 - 检查该分区是否被显式引用在未提交事务中(如
SELECT ... FROM t PARTITION(p202401) FOR UPDATE),否则会阻塞直到事务结束
替代方案对比:TRUNCATE PARTITION vs DROP + READD PARTITION
某些场景下(如需重置自增 ID 或释放磁盘空间更彻底),可考虑 ALTER TABLE t DROP PARTITION p202401, ADD PARTITION (...)。但注意:DROP PARTITION 会重建分区结构,耗时更长,且期间对该分区的 DML 会被阻塞;而 TRUNCATE PARTITION 是原子操作,速度更快、影响窗口更短。
最易被忽略的一点:MySQL 8.0.23+ 才支持对二级分区(SUBPARTITION)单独 TRUNCATE;低版本只能清空整个一级分区,哪怕你只想清理其中某个子分区。










