Mysql

关注公众号 jb51net

关闭
首页 > 数据库 > Mysql > MySQL数据离线迁移

MySQL进行数据离线迁移的实现方案

作者:西门吹雪分身

在实际的业务需求中,mysql数据库往往需要从一个服务器迁移或者导出到另外一台服务器,这个数据导入导出的工作,是不可避免的,所以本文介绍了MySQL数据迁移的物理操作方式,需要的朋友可以参考下

在实际的业务需求中,mysql数据库往往需要从一个服务器迁移或者导出到另外一台服务器。这个数据导入导出的工作,是不可避免的。

mysql对于数据的导入导出提供了逻辑操作与物理操作两种方式,其中mysqdump的逻辑操作往往需要生成SQL文件,如果数据量比较大,可能执行的效果比较差,耗时比较长。本文主要介绍一下基于mysql文件层面的物理操作,也可以叫做冷备份。

mysql的相关官网说明

mysql官网

Transportable Tablespace(可传输表空间) 是 MySQL InnoDB 存储引擎提供的一种机制,允许用户将某个表的表空间文件(.ibd)及其元数据校验文件(.cfg)从一台服务器“运输”到另一台服务器,并直接挂载到目标数据库的表结构上。

核心原理
InnoDB 表空间文件内部包含了一个唯一的 Tablespace ID 和 Schema 指纹。直接拷贝 .ibd 文件时,目标库的元数据(Data Dictionary)中记录的 ID 与文件内部的 ID 不一致,导致无法识别。

详细的操作流程

假设我们要迁移表 users,数据库为 test_db。

前提条件:

第一阶段:在源库(Source)生成文件

这一步的目的是获取一份一致性快照数据文件配套的校验文件

  1. 确保表是可传输的(通常默认就是,但显式执行一次更稳妥):
USE test_db;
-- 这一步会刷新脏页到磁盘,并锁定表进行元数据冻结
FLUSH TABLES users FOR EXPORT;

注意:执行此命令后,表 users 会被锁定为只读(Read Only),直到你解锁或复制完文件。其他会话对该表的写操作会被阻塞。

  1. 复制文件
    保持终端窗口不关闭(保持锁状态),打开另一个终端或通过脚本复制文件。
    找到数据目录(通常是 /var/lib/mysql/test_db/):
    • users.ibd:数据文件。
    • users.cfg:关键文件,包含元数据校验信息。
# 在另一个终端执行
cp /var/lib/mysql/test_db/users.{ibd,cfg} /tmp/backup_for_migration/

# 确认文件已复制完成
ls -lh /tmp/backup_for_migration/
  1. 解锁源库
    文件复制完成后,必须立即解锁,恢复业务写入。
    回到第一个执行 SQL 的终端:
UNLOCK TABLES;

此时源库业务恢复正常。

第二阶段:在目标库(Target)准备环境

  1. 创建结构一致的表
    在目标库执行与源库完全相同的 CREATE TABLE 语句。
CREATE DATABASE IF NOT EXISTS test_db;
USE test_db;

CREATE TABLE users (
    id INT UNSIGNED AUTO_INCREMENT PRIMARY KEY,
    username VARCHAR(50) NOT NULL,
    email VARCHAR(100),
    created_at TIMESTAMP DEFAULT CURRENT_TIMESTAMP
    -- 必须与源库完全一致,包括字符集、排序规则、索引
) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_0900_ai_ci;

提示:可以用 SHOW CREATE TABLE users\G 在源库查看精确语句。

  1. 丢弃自动生成的表空间:

刚才建表时,InnoDB 已经生成了一个空的 users.ibd。需要删掉它,以便导入旧的。

ALTER TABLE users DISCARD TABLESPACE;

执行后,去操作系统查看 /var/lib/mysql/test_db/users.ibd,它应该已经消失了。此时表存在,但无法读写数据。

第三阶段:导入文件到目标库

  1. 拷贝文件到目标数据目录:
    将第一阶段生成的 users.ibd 和 users.cfg 上传到目标库对应的数据目录。
# 假设文件在 /tmp/backup_for_migration/
cp /tmp/backup_for_migration/users.{ibd,cfg} /var/lib/mysql/test_db/
  1. 修正文件权限(至关重要):
    MySQL 进程通常以 mysql 用户运行。如果文件归属是 root,导入会失败。
chown mysql:mysql /var/lib/mysql/test_db/users.{ibd,cfg}
chmod 660 /var/lib/mysql/test_db/users.{ibd,cfg}
  1. 执行导入命令
    登录目标库 MySQL:
USE test_db;
ALTER TABLE users IMPORT TABLESPACE;

  1. 验证数据:
SELECT COUNT(*) FROM users;
SELECT * FROM users LIMIT 5;

特点与限制

优点

  1. 速度极快:不涉及逻辑导出(SQL 生成)和导入(SQL 解析执行),本质是文件拷贝,适合 TB 级大表迁移。
  2. 节省 IO:不会像 mysqldump 那样产生巨大的重做日志(Redo Log)和二进制日志(Binlog)压力(导入时可以暂时关闭 Binlog)。
  3. 支持分区表:可以单独导入某个分区,也可以导入整个分区表。

限制与注意事项

4. 版本严格限制:

  1. 架构一致:
  1. 只针对 InnoDB:MyISAM 或其他引擎不适用。
  2. 外键约束:如果表之间有外键约束,导入过程可能会比较复杂,建议先禁用外键检查 (SET FOREIGN_KEY_CHECKS=0),导入后再开启。
  3. 只读窗口:在源库执行 FLUSH TABLES … FOR EXPORT 期间,该表是只读的。虽然时间很短(仅拷贝文件的时间),但在高并发场景下仍需注意。

总结

Transportable Tablespace 是 MySQL 官方提供的“物理备份/迁移”方案。

以上就是MySQL进行数据离线迁移的实现方案的详细内容,更多关于MySQL数据离线迁移的资料请关注脚本之家其它相关文章!

您可能感兴趣的文章:
阅读全文