第 49.1 节:主从复制设置

考虑两台 MySQL 服务器用于复制设置:一台是主库(Master),另一台是从库(Slave)。

我们将配置主库,使其记录对其执行的每个操作。然后配置从库,使其查看主库上的日志,当主库的日志中发生变化时,从库执行相同的操作。

主库配置

首先,需要在主库上创建一个用户。该用户将供从库用于建立与主库的连接。

CREATE USER 'user_name'@'%' IDENTIFIED BY 'user_password';
GRANT REPLICATION SLAVE ON *.* TO 'user_name'@'%';
FLUSH PRIVILEGES;

将 user_name 和 user_password 替换为你的用户名和密码。

然后编辑 my.ini(Linux 中为 my.cnf)文件。在 [mysqld] 部分添加以下行:

server-id = 1
log-bin = mysql-bin.log
binlog-do-db = your_database
  • 第一行为该 MySQL 服务器分配一个 ID。
  • 第二行告诉 MySQL 开始将日志写入指定的日志文件。在 Linux 中可配置为 log-bin = /home/mysql/logs/mysql-bin.log。如果你在已经使用过复制的 MySQL 服务器上启动复制,请确保该目录为空,不包含任何复制日志。
  • 第三行指定要记录日志的数据库。将 your_database 替换为你的数据库名称。

确保 skip-networking 未被启用,然后重启 MySQL 服务器(主库)。

从库配置

同样,在从库上编辑 my.ini 文件。在 [mysqld] 部分添加以下行:

server-id = 2
master-host = master_ip_address
master-connect-retry = 60
master-user = user_name
master-password = user_password
replicate-do-db = your_database
relay-log = slave-relay.log
relay-log-index = slave-relay-log.index
  • 第一行为该 MySQL 服务器分配一个 ID,该 ID 必须唯一。
  • 第二行为主库的 IP 地址。
  • 第三行设置重试间隔(秒)。
  • 接下来的两行告诉从库连接主库时使用的用户名和密码。
  • 下一行指定需要复制的数据库。
  • 最后两行指定中继日志和中继日志索引文件的名称。

确保 skip-networking 未被启用,然后重启 MySQL 服务器(从库)。

将数据拷贝到从库

如果数据在主库上不断被添加,则需要阻止对主库的所有数据库访问,以便无法添加新数据。这可以通过在主库上执行以下语句实现:

FLUSH TABLES WITH READ LOCK;

如果没有数据正在被添加,可以跳过上述步骤。

使用 mysqldump 备份主库数据:

mysqldump your_database -u root -p > D://Backup/backup.sql;

将 your_database 和备份目录替换为你的实际设置。现在,给定位置将有一个名为 backup.sql 的文件。

如果从库上不存在该数据库,则创建它:

CREATE DATABASE your_database;

然后将备份导入从库:

mysql -u root -p your_database < D://Backup/backup.sql

启动复制

要启动复制,需要找到主库上的日志文件名和日志位置。在主库上执行:

SHOW MASTER STATUS;

[图片占位符:输出示例]

然后在从库上执行:

SLAVE STOP;
CHANGE MASTER TO
    MASTER_HOST='master_ip_address',
    MASTER_USER='user_name',
    MASTER_PASSWORD='user_password',
    MASTER_LOG_FILE='mysql-bin.000001',   -- 使用 SHOW MASTER STATUS 中的值
    MASTER_LOG_POS=123;                   -- 使用 SHOW MASTER STATUS 中的值
SLAVE START;

首先停止从库。然后告诉它确切地在主库日志文件的哪个位置开始读取。将 MASTER_LOG_FILE 和 MASTER_LOG_POS 替换为在主库上运行 SHOW MASTER STATUS 获得的值。

修改 MASTER_HOST 为主库的 IP,并根据需要修改用户名和密码。

现在从库将处于等待状态。可以通过以下命令查看从库状态:

SHOW SLAVE STATUS;

如果你之前执行了 FLUSH TABLES WITH READ LOCK,请解锁表:

UNLOCK TABLES;

现在主库会记录对其执行的每个操作,从库会查看主库的日志,当主库的日志中发生变化时,从库会进行复制。

第 49.2 节:复制错误

在从库上运行查询时,如果发生错误,MySQL 会自动停止复制,以便识别问题并修复。这通常是因为某个事件导致了重复键,或者找不到要更新或删除的行。你可以跳过此类错误,尽管不推荐这样做。

要跳过导致从库挂起的单个查询,使用以下语法:

SET GLOBAL sql_slave_skip_counter = N;

该语句跳过主库的下 N 个事件。仅在从库线程未运行时有效,否则会产生错误。

STOP SLAVE;
SET GLOBAL sql_slave_skip_counter = 1;
START SLAVE;

在某些情况下这是可行的。但如果该语句是多语句事务的一部分,情况会变得更复杂,因为跳过产生错误的语句会导致整个事务被跳过。

如果你想跳过更多产生相同错误代码的查询,并且确信跳过这些错误不会导致从库不一致,可以在 my.cnf 中添加一行来跳过该错误代码。

例如,要跳过重复键错误(错误代码 1062):

slave-skip-errors = 1062

你也可以跳过其他类型的错误或跳过所有错误代码,但必须确保跳过这些错误不会导致从库不一致。语法和示例如下:

slave-skip-errors = [err_code1,err_code2,... | all]
slave-skip-errors = 1062,1053
slave-skip-errors = all
slave-skip-errors = ddl_exist_errors