先执行lsof +l1查被删除但进程仍在写入的“幽灵文件”,再根据文件类型选择kill进程、重启服务或安全清理;df与du差异主因是文件系统统计逻辑不同,非磁盘真满。

df -h 显示 100% 但 du 总和远小于此,怎么破?
这不是磁盘真满了,而是“幽灵文件”在作祟:进程还在写某个已被删除的文件(比如没退出的 mysqldump、卡住的 binlog 写入),df 统计了已删但未释放的空间,du 却看不见它。
- 立刻执行
lsof +L1,找出状态为deleted的大文件,重点关注/var/lib/mysql/下的#sql_*、ibtmp1、mysql-bin.* - 确认无活跃
mysqld进程(ps aux | grep mysqld),再清理:sudo find /var/lib/mysql -name "#sql_*" -mmin +30 -delete -
ibtmp1占用大且 MySQL ≥ 5.7.30?可用ALTER TABLESPACE innodb_temp_tablespaces ENCRYPTION='N';触发释放;否则必须停服务后手动删
PURGE BINARY LOGS 后主从断了,为什么?
盲目清 binlog 是最常踩的坑——PURGE 不看从库进度,直接删掉从库还没读完的日志,主从立刻失联。
- 先查从库状态:
SHOW SLAVE STATUS\G,记下Relay_Master_Log_File和Exec_Master_Log_Pos - 再查当前 binlog 列表:
SHOW BINARY LOGS;,确保你要PURGE的文件名早于Relay_Master_Log_File - 安全命令只用时间锚点:
PURGE BINARY LOGS BEFORE '2026-06-25 00:00:00';(比当前时间早 1 天) - 长期预防:在
my.cnf中设expire_logs_days = 3,并验证生效:SELECT @@expire_logs_days;
DELETE 了 90% 数据,.ibd 文件大小纹丝不动
InnoDB 设计上就不把已删行的空间还给文件系统,这是正常行为,不是 bug。不干预的话,空间永远卡在峰值。
- 确认
innodb_file_per_table = ON(默认开启),否则所有表共用ibdata1,删表也无效 - 线上表可执行
ALTER TABLE t1 ENGINE=InnoDB;,效果同OPTIMIZE TABLE,语义更清晰 - 若表太大不敢锁,且业务不能停写,别硬扛:用
pt-online-schema-change或导出+DROP+重建(务必提前停写或加锁) -
TRUNCATE TABLE比DELETE FROM快得多,且立即释放空间,但不可回滚、重置自增 ID
安装 MySQL 失败报 “No space left on device”,但 df -h / 显示还有 50GB
90% 的情况是卡在 /tmp 或 /var/tmp 上——这两个目录常为 tmpfs(内存挂载),大小仅 RAM/2 或固定 2–4GB,而 MySQL 初始化需 3–8GB 临时空间。
- 定位瓶颈:
df -h | grep -E '(tmp|var)'看真实使用率;ls -ld /tmp确认是否 tmpfs - 绕过限制:安装前设环境变量
TMPDIR=/data/tmp;APT 安装用sudo apt -o DPkg::Install::TempDir=/data/tmp install mysql-server - 安装完成后立刻改配置:在
[mysqld]段加datadir = /data/mysql和tmpdir = /data/mysql-tmp,同步权限与 SELinux 上下文
read_only=0 只是开关,不是解药;OPTIMIZE TABLE 在大表上会锁表;/tmp 是内存盘这件事,很多人直到重装三次才意识到。











