新SSD必须先挂载并格式化为ext4且挂载到/data,再通过rsync迁移数据、修正属主、更新my.cnf中datadir及socket/pid-file路径,最后配置SELinux/AppArmor策略并验证启动。

确认新SSD已正确挂载且文件系统就绪
别急着改MySQL配置,先确保物理盘可用。执行 lsblk -f,看到类似 /dev/vdb1 ext4 ... /data 这样的输出才算到位。如果 MOUNTPOINT 为空,说明还没挂载;如果挂载点是 /mnt 或临时路径,也得改——生产环境必须用固定、语义清晰的路径,比如 /data/mysql。
常见错误现象:挂载后 df -h 显示容量正常,但 touch /data/test 报 Permission denied。这通常是文件系统没格式化(mkfs.ext4 /dev/vdb1 漏了),或挂载时用了 noexec/nosuid 等限制选项。
- 格式化前务必确认设备名准确(
lsblk或fdisk -l),误操作/dev/vda1会丢系统 - 挂载命令推荐用
sudo mount /dev/vdb1 /data,然后写入/etc/fstab永久生效:/dev/vdb1 /data ext4 defaults,noatime 0 2 -
noatime能减少IO,对数据库写密集场景有实际收益
停服务 + 安全拷贝数据到新路径
MySQL必须完全停止才能迁移数据,否则 ibdata1、redo log 等文件状态不一致,启动直接失败。执行 sudo systemctl stop mysqld(CentOS/RHEL)或 sudo systemctl stop mysql(Ubuntu/Debian),再用 ps aux | grep mysql 确认无残留进程。
不要用 mv 直接搬目录。一旦权限出错或磁盘满,MySQL无法启动,又没备份,就是事故现场。必须用 rsync 做原子性同步:
sudo rsync -avh --progress /var/lib/mysql/ /data/mysql/
同步完立刻修正属主:sudo chown -R mysql:mysql /data/mysql。漏掉这步,MySQL 启动时会报 Can't open the mysql.plugin table 或直接拒绝加载InnoDB引擎。
-
rsync的-a保留权限、时间戳、软链;-v和--progress方便观察进度和排查中断 - 目标路径
/data/mysql必须为空目录,否则rsync会把源目录整个塞进去,变成/data/mysql/var/lib/mysql - 同步后检查关键文件是否存在:
ls -l /data/mysql/ibdata1、ls -l /data/mysql/mysql/user.frm(MySQL 5.7)或mysql/user.ibd(8.0+)
修改my.cnf并绕过SELinux/AppArmor拦截
MySQL只认配置文件里写的 datadir,改路径第一步就是让它“知道”新位置在哪。编辑 /etc/my.cnf(RHEL/CentOS)或 /etc/mysql/my.cnf(Debian/Ubuntu),在 [mysqld] 段下添加:
面向 CRM 系统的 MySQL 8 数据库模式设计。当用户需要为客户关系管理(CRM)系统设计、评审、优化或生成数据库模式时,应使用此项技能。
datadir = /data/mysql
注意:不要注释旧行,也不要加多余空格或斜杠;改完用 mysqld --validate-config(MySQL 5.7.19+)或 mysqld --verbose --help | grep datadir 验证是否被正确读取。
即使配置改对、文件拷全、属主修好,Linux安全模块仍可能拦住启动。典型表现是 systemctl start mysqld 无声失败,journalctl -u mysqld 里只有模糊的 Operation not permitted。
- Ubuntu/Debian(AppArmor):编辑
/etc/apparmor.d/usr.sbin.mysqld,在/var/lib/mysql/** rwk,下新增一行/data/mysql/** rwk,,再执行sudo apparmor_parser -r /etc/apparmor.d/usr.sbin.mysqld - CentOS/RHEL(SELinux):运行
sudo semanage fcontext -a -t mysqld_db_t "/data/mysql(/.*)?",再sudo restorecon -Rv /data/mysql - 如果不确定是否启用,先查:
getenforce(SELinux)、aa-status(AppArmor)
验证启动与权限细节
启动前再做一次快速检查:sudo -u mysql ls -l /data/mysql 确保 mysql 用户能读写;sudo -u mysql mysql --socket=/tmp/mysql.sock -e "SELECT 1"(如果 socket 还在默认位置)只是辅助测试,真正要跑的是 sudo systemctl start mysqld 后连上去看状态。
容易被忽略的关键点:
-
socket和pid-file路径也要同步更新,否则客户端连不上或服务无法被管理:socket = /data/mysql/mysql.sock<br>pid-file = /data/mysql/mysqld.pid
- 如果原
my.cnf里有tmpdir,也建议改成/data/tmp并chown mysql:mysql /data/tmp,避免临时表写爆系统盘 - 首次启动成功后,立刻执行
mysql -uroot -p -e "SHOW VARIABLES LIKE 'datadir';"确认返回值确实是/data/mysql,别信配置文件,信运行时结果










