第 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