最稳妥的mysql迁移路径是mysqldump导出加mysql导入,需加--single-transaction、--routines、--triggers、--set-gtid-purged=off和--default-character-set=utf8mb4参数,并确保目标库字符集为utf8mb4,导入时设置--max-allowed-packet避免超限中断。

直接用 mysqldump 导出 + mysql 导入是最稳妥、兼容性最好、也最常被忽略细节的路径。别碰物理备份,除非你明确知道云厂商用的是什么版本、什么存储引擎、有没有启用加密或压缩——绝大多数人掉坑都在这儿。
导出本地数据库时必须加这几个参数
不加就容易丢数据、乱编码、权限错乱:
-
--single-transaction:对 InnoDB 表做一致性快照,避免锁表(但不能保证 MyISAM 一致) -
--routines和--triggers:否则存储过程、触发器不会导出 -
--set-gtid-purged=OFF:云 MySQL 实例大多开启 GTID,但本地没开时导入会报错ERROR 1840 (HY000): @@GLOBAL.GTID_PURGED can only be set when @@GLOBAL.GTID_EXECUTED is empty -
--default-character-set=utf8mb4:显式指定字符集,防止导出文件默认用 latin1 导致 emoji 或中文乱码
完整命令示例:mysqldump -h127.0.0.1 -P3306 -uroot -p --single-transaction --routines --triggers --set-gtid-purged=OFF --default-character-set=utf8mb4 mydb > mydb.sql
导入前必须在云数据库里建空库并确认字符集
云平台创建的数据库默认字符集未必是 utf8mb4,尤其老实例可能还是 utf8(实际只支持 3 字节),导入时会 silently 截断 emoji 或某些生僻字。
执行前先连上云数据库检查:mysql -h your-rds-endpoint -P3306 -uadmin -p -e "SHOW CREATE DATABASE mydb;"
如果显示不是 DEFAULT CHARACTER SET = utf8mb4 COLLATE = utf8mb4_unicode_ci,就立刻重建:DROP DATABASE IF EXISTS mydb; CREATE DATABASE mydb CHARACTER SET utf8mb4 COLLATE utf8mb4_unicode_ci;
导入命令要避开常见 timeout 和 packet 错误
云数据库通常限制 max_allowed_packet(默认 4MB)和连接超时(如 30 秒),大 SQL 文件一卡就中断。
- 加
--max-allowed-packet=512M参数(值不能超过云实例允许上限,查SHOW VARIABLES LIKE 'max_allowed_packet';) - 禁用 autocommit 加速导入:
mysql -h ... -u... -p --max-allowed-packet=512M mydb 不够稳;改用交互式导入:<br><code>mysql -h ... -u... -p mydb→ 进入后执行:SET autocommit=0; SOURCE /path/to/mydb.sql; COMMIT; - 如果文件太大,用
split -l 1000 mydb.sql chunk_拆成小文件再逐个导入,避免单次失败全盘重来
导入后必须验证三件事
很多人以为“没报错就算成功”,结果发现视图没建、外键失效、时间字段全变成 0000-00-00:
- 查行数是否对得上:
SELECT COUNT(*) FROM table1;对比本地和云上 - 查关键约束:
SELECT CONSTRAINT_NAME, CONSTRAINT_TYPE FROM information_schema.TABLE_CONSTRAINTS WHERE TABLE_SCHEMA='mydb';看 FOREIGN KEY 是否还在 - 查时间字段是否异常:
SELECT * FROM table_with_datetime LIMIT 1;看created_at类字段有没有变成0000-00-00 00:00:00—— 如果有,说明导出时没加--skip-tz-utc或云实例sql_mode含NO_ZERO_DATE
真正麻烦的从来不是“怎么导”,而是“导完看起来像对了,其实漏了关键元数据”。每一步都得验,尤其是 routines、triggers、charset、sql_mode 这四个点,一个没对齐,上线就出问题。











