一、警报响起:磁盘空间100%意味着什么
监控系统发出告警:/dev/mapper/vg-root 使用率已飙升至98%,应用日志写入失败,数据库事务回滚。这不是演习,磁盘空间满额会直接导致服务崩溃、数据丢失、甚至系统无法正常关机。面对这种紧急情况,运维人员需要在最短时间内做出判断——先扩容,还是先清理?
如果你的服务器采用LVM(Logical Volume Manager)管理磁盘,那么在线扩容是最优解,因为它可以无重启、无停机地增加逻辑卷容量。但扩容前必须确保物理卷(PV)有空闲空间,或者能通过新增硬盘/扩容云磁盘来扩展卷组(VG)。另一条路径是立即清理大文件,释放空间以恢复业务写入。本文将从两条线并行展开,教你如何在10分钟内止血,30分钟内根治。
二、紧急止血:先清理还是先扩容?
2.1 判断根因与风险等级
首先执行 df -h 和 df -i 确认是空间耗尽还是inode耗尽。如果是inode耗尽(大量小文件),扩容也无法解决,必须清理。对于空间满额的情况,考虑以下因素:
- 扩容可行性:物理卷是否有空闲PE?执行
vgdisplay查看 Free PE 数量。若没有,则需要添加新磁盘或扩容底层存储。 - 业务容忍度:如果是非核心日志分区(如 /var/log),可以先清理;如果是数据盘(如 /data/mysql),扩容更为安全。
- 操作时间窗口:扩容命令几乎瞬时完成,但扩容底层磁盘可能需要时间。清理则需要扫描和删除,可能影响I/O。
建议优先级:先扩容(若可行)→ 再清理冗余文件。因为扩容不会误删数据,而清理操作可能存在风险。
三、LVM在线扩容:三步搞定,无需重启
3.1 前提条件检查
假设你的服务器是云服务器(如AWS EBS、阿里云ESSD),可以在控制台扩容磁盘后,再在系统内识别新空间。物理机则需要插入新硬盘。以下为通用流程:
- 确认逻辑卷挂载点:
lsblk或mount | grep lvm,确定要扩容的LV路径,例如 /dev/vg_data/lv_data。 - 检查卷组剩余空间:
vgdisplay vg_data,关注 Free PE / Size。 - 若VG无空间,需扩展VG:
- 新增物理卷:
pvcreate /dev/sdb - 加入卷组:
vgextend vg_data /dev/sdb
- 新增物理卷:
3.2 执行逻辑卷扩容
使用 lvextend 命令增加LV大小,推荐直接指定增减容量或目标大小:
# 增加10GB
lvextend -L +10G /dev/vg_data/lv_data
# 或者扩展到50GB
lvextend -L 50G /dev/vg_data/lv_data
注意:如果文件系统是ext4,扩容后需要执行 resize2fs;如果是xfs,执行 xfs_growfs。不同文件系统的在线调整命令不同,搞混会导致数据损坏。
3.3 调整文件系统大小
以最常见的ext4为例:
resize2fs /dev/vg_data/lv_data
对于XFS:
xfs_growfs /mount/point
验证最终结果:df -h 确认新大小生效。整个过程无需卸载分区,不影响业务。
- 云服务器扩容磁盘后,需要执行
partprobe或重启云助手才能识别新分区,但LVM扩容通常无需分区。 - 如果LV用于数据库,扩容后最好让数据库重新计算表空间(如MySQL的
ALTER TABLE ... ENGINE=InnoDB),但这不是必须的。
四、大文件清理:定位与清除实战
4.1 快速定位空间占用大户
使用 du -sh /* 或 ncdu(需安装)逐级扫描。更高效的方式是:
# 查看当前目录下各个子目录大小(深度1)
du -sh * | sort -rh | head -20
# 查看文件系统根目录下各目录大小
du -sh /[a-z]* | sort -rh | head -10
若磁盘已满导致命令卡死,可以切换到其他未满分区执行,或使用 timeout 30 du ... 限时。
4.2 常见可清除的大文件类型
- 应用日志:/var/log 下 messages、syslog、tomcat、nginx、mysql 等日志文件,按天轮转。
- 审计日志:/var/log/audit 或 /var/log/secure,可配置保留周期。
- 临时文件:/tmp、/var/tmp、/dev/shm(内存磁盘)中的大文件。
- Docker容器:/var/lib/docker/overlay2 下的无归属层,使用
docker system prune清理。 - 系统转储:core dump 文件,
find / -name core -type f -size +100M。 - 邮件队列:/var/spool/postfix/maildrop 等。
4.3 安全清理命令范例
# 清空日志文件(保留文件句柄,不重启服务)
cat /dev/null > /var/log/messages
# 删除3天前的日志文件
find /var/log -name "*.log.*" -mtime +3 -delete
# 清理Docker无用数据
docker system prune -af --volumes
# 清理apt/ yum缓存
apt-get clean # Debian/Ubuntu
yum clean all # CentOS/RHEL
注意:不要用 rm -f 删除正在被进程打开的文件,否则空间不会立即释放。正确做法是使用 cat /dev/null > file 或 truncate -s 0 file 清空内容。
五、验证与回滚:确保万无一失
5.1 扩容后的验证
- 文件系统检查:
df -h显示新容量,fdisk -l确认物理磁盘大小。 - 数据完整性:如果是数据库所在的LV,执行
mysqlcheck或CHECK TABLE测试。 - 监控恢复:确认警报消失,磁盘使用率低于阈值。
5.2 清理操作的容错
建议先列出待删除文件:
find /var/log -name "*.gz" -mtime +7 | xargs ls -lh
确认无误后再执行删除。
若误删重要文件,立即停写并尝试恢复:lsof | grep deleted 找到仍在运行的进程,从 /proc/文件描述符 中复制。
六、长期防御:建立自动化机制
6.1 配置logrotate
确保所有应用日志启用轮转,示例配置:
/var/log/app/*.log {
daily
rotate 7
compress
delaycompress
missingok
notifempty
}
6.2 设置磁盘空间预警
利用Prometheus + Node Exporter 或 Zabbix,在磁盘使用率达到85%时发出警告,90%触发自动扩容脚本(如AWS Lambda 或 ansible)。
6.3 定期审计大文件
每周定时任务:
0 2 * * 1 /usr/bin/du -sh /var/log | sort -rh | mail -s "磁盘报告" admin@example.com
七、常见误区与风险规避
- 误区:扩容前不备份数据——虽然后果不严重,但操作失误可能损坏LV元数据。重要数据建议先快照。
- 误区:使用 rm 删除正在打开的日志文件——空间不释放,且造成死句柄。始终用截断方式。
- 误区:忽略inode使用率——如果inode用满,即使空间充裕也无法创建新文件。使用
tune2fs -m 0或扩容解决。 - 误区:云平台直接扩容不给系统识别——需执行
lsblk重新扫描总线,或使用echo 1 > /sys/block/sda/device/rescan。
结语
磁盘空间满额是运维工程师的“必修课”,掌握LVM在线扩容和大文件清理可以让你在数分钟内化险为夷。但更重要的是建立预防机制:日志轮转、监控告警、自动化扩容流程。下次警报响起时,你不再慌张,而是胸有成竹地敲下那些经过验证的命令。
如果你想深入学习LVM的高级特性(快照、thin provisioning),或者清理特定中间件的日志(如Elasticsearch、Kafka),欢迎在评论区留言,我们会在后续文章详细讲解。
延伸阅读
