前情提要:本文将详细讲解数据库主从架构的两种常见模式------一主一从和一主两从。内容包括架构原理、适用场景说明,并提供完整的配置指南,涵盖主库/从库设置以及新从库加入流程。通过本文,您将掌握数据库主从架构的完整部署方法。
一、主从架构介绍
数据库的主从架构是通过将数据从一个主库复制到一个或多个从库来实现,该架构的核心是数据同步,主要用于数据的容灾备份,读写分离,数据分析场景中。
二、实验环境
系统:RHEL9.3
主机情况清单:
|-------------|---------------|--------|
| 主机名 | IP地址 | 身份 |
| mysql-node1 | 172.25.254.10 | master |
| mysql-node2 | 172.25.254.20 | slave |
| mysql-node3 | 172.25.254.30 | slave |
三、一主一从架构配置
3.1 master主机配置
- 编辑mysql配置文件
bash
[root@mysql-node1 ~]# vim /etc/my.cnf
[mysqld]
datadir=/data/mysql
socket=/data/mysql/mysql.sock
symbolic-links=0
log-bin=mysql-bin
server-id=10
# [mysqld]
# 这是配置段的标识,表示下面的配置项适用于MySQL服务器进程(mysqld)
# MySQL配置文件可以有多个段,如 [client]、[mysql]、[mysqld_safe]等,每个段针对不同的组件
# datadir=/data/mysql
# 指定MySQL数据文件的存储目录
# 这是MySQL最重要的目录,包含:所有数据库的表数据文件(.ibd, .frm, .MYD等),系统表空间(ibdata1),重做日志(ib_logfile*),二进制日志(如果启用),错误日志(如果配置在此),默认值通常是 /var/lib/mysql
# socket=/data/mysql/mysql.sock
# 指定MySQL的Unix域套接字文件路径
# 这是本地客户端连接MySQL服务器时使用的文件,当客户端和服务器在同一台机器上时,通过socket文件连接比TCP/IP更快,默认值通常是 /var/lib/mysql/mysql.sock,需要确保MySQL用户有权限读写这个文件
# symbolic-links=0
# 禁用符号链接功能
# 当设置为0时,MySQL不允许使用符号链接来链接数据库目录或表文件,这是安全考虑,防止通过符号链接访问系统其他文件,在生产环境中通常建议禁用,如果设置为1,则允许使用符号链接
# log-bin=mysql-bin
# 启用二进制日志(binlog)并指定日志文件的基本名称
# server-id=1
# 为MySQL服务器设置唯一标识符
# 在主从复制环境中,每个MySQL实例必须有唯一的server-id
- 重启mysql服务并检验配置是否生效
bash
# 重启服务
[root@mysql-node1 ~]# /etc/init.d/mysqld restart # systemctl restart mysqld需要编译时添加参数
# 验证
mysql> select @@server_id;
+-------------+
| @@server_id |
+-------------+
| 10 |
+-------------+
1 row in set (0.00 sec)
mysql> SELECT @@global.log_bin; # 检验二进制文件是否生效
+------------------+
| @@global.log_bin |
+------------------+
| 1 |
+------------------+
1 row in set (0.00 sec)
可见配置文件生效
- 在数据库中创建主从复制专用账户并授权
bash
# 查看默认认证插件
mysql> SHOW VARIABLES LIKE 'default_authentication_plugin';
+-------------------------------+-----------------------+
| Variable_name | Value |
+-------------------------------+-----------------------+
| default_authentication_plugin | caching_sha2_password |
+-------------------------------+-----------------------+
1 row in set (0.01 sec)
# 该插件默认要求身份验证,而主从同步中一般都在内网进行,因此主从复制账户不考虑使用这个使用默认插件
# 创建主从复制账户
mysql> create user dragon@'%' identified with mysql_native_password by '123'; # mysql_native_passwd不要求身份验证
# 授权允许用户连接到主服务器并请求二进制日志(用于主从复制)
mysql> GRANT replication slave ON *.* to dragon@'%';
mysql> show master status\G # 查看master状态
*************************** 1. row ***************************
File: mysql-bin.000011
Position: 238
Binlog_Do_DB:
Binlog_Ignore_DB:
Executed_Gtid_Set: 00edb57b-12b8-11f1-a822-000c29d050f7:1-8,
b7633ffa-12b4-11f1-90ce-000c29d81805:1-3
1 row in set, 1 warning (0.00 sec)
# File:这是主库当前正在写入的二进制日志文件名
# Position:这是下一个事件将要被写入的位置点(以字节为单位),它表示在当前的 File(即 mysql-bin.000011)中,已经写到了第 238 字节处,下一个事件将从这里开始记录,这个数字会随着主库不断产生新的数据变更(写入事件)而持续增长。
# 这两个参数是建立主从复制的关键信息
3.2 slave节点配置
- 编辑配置文件,重启mysqld
bash
[root@mysql-node2 ~]# vim /etc/my.cnf
[mysqld]
datadir=/data/mysql
socket=/data/mysql/mysql.sock
symbolic-links=0
server-id=20
log-bin=mysql-bin
[root@mysql-node2 ~]# /etc/init.d/mysqld restart
- 开启主从复制
bash
mysql> CHANGE MASTER TO MASTER_HOST='172.25.254.10',MASTER_USER='dragon',MASTER_PASSWORD='123',MASTER_LOG_FILE='mysql-bin.000011',MASTER_LOG_POS=238; # 后面两个参数应该与主服务器状态一致
# 完整命令解析
CHANGE MASTER TO
MASTER_HOST='172.25.254.10', -- 主服务器地址
MASTER_USER='lee', -- 复制用户名
MASTER_PASSWORD='lee', -- 复制用户密码
MASTER_PORT=3306, -- 主服务器端口(默认3306,可省略)
MASTER_LOG_FILE='mysql-bin.000011', -- 二进制日志文件名
MASTER_LOG_POS=238, -- 开始复制的位置
MASTER_CONNECT_RETRY=60, -- 连接重试间隔(秒)
MASTER_RETRY_COUNT=86400, -- 重试次数
MASTER_AUTO_POSITION=0, -- 是否使用GTID自动定位(0=否,1=是)
MASTER_SSL=0; -- 是否使用SSL连接
bash
# 开启主从复制
mysql> start slave;
Query OK, 0 rows affected, 2 warnings (0.00 sec)
mysql> show slave status\G
*************************** 1. row ***************************
Slave_IO_State: Waiting for source to send event
Master_Host: 172.25.254.10
Master_User: dragon
Master_Port: 3306
Connect_Retry: 60
Master_Log_File: mysql-bin.000011
Read_Master_Log_Pos: 238
Relay_Log_File: mysql-node2-relay-bin.000008
Relay_Log_Pos: 375
Relay_Master_Log_File: mysql-bin.000011
Slave_IO_Running: Yes # 注意该参数必须为yes
Slave_SQL_Running: Yes # 注意该参数必须为yes
Replicate_Do_DB:
Replicate_Ignore_DB:
Replicate_Do_Table:
Replicate_Ignore_Table:
Replicate_Wild_Do_Table:
Replicate_Wild_Ignore_Table:
Last_Errno: 0
Last_Error:
Skip_Counter: 0
Exec_Master_Log_Pos: 238
Relay_Log_Space: 592
Until_Condition: None
Until_Log_File:
Until_Log_Pos: 0
Master_SSL_Allowed: No
Master_SSL_CA_File:
Master_SSL_CA_Path:
Master_SSL_Cert:
Master_SSL_Cipher:
Master_SSL_Key:
Seconds_Behind_Master: 0
Master_SSL_Verify_Server_Cert: No
Last_IO_Errno: 0
Last_IO_Error:
Last_SQL_Errno: 0
Last_SQL_Error:
Replicate_Ignore_Server_Ids:
Master_Server_Id: 10
Master_UUID: b7633ffa-12b4-11f1-90ce-000c29d81805
Master_Info_File: mysql.slave_master_info
SQL_Delay: 60
SQL_Remaining_Delay: NULL
Slave_SQL_Running_State: Replica has read all relay log; waiting for more updates
Master_Retry_Count: 10
Master_Bind:
Last_IO_Error_Timestamp:
Last_SQL_Error_Timestamp:
Master_SSL_Crl:
Master_SSL_Crlpath:
Retrieved_Gtid_Set:
Executed_Gtid_Set: 00edb57b-12b8-11f1-a822-000c29d050f7:1-8,
b7633ffa-12b4-11f1-90ce-000c29d81805:1-3
Auto_Position: 1
Replicate_Rewrite_DB:
Channel_Name:
Master_TLS_Version:
Master_public_key_path:
Get_master_public_key: 0
Network_Namespace:
1 row in set, 1 warning (0.01 sec)
- 注意:若从节点配置错误可以清空后重新配置
bash
mysql> RESET SLAVE ALL;
Query OK, 0 rows affected, 1 warning (0.00 sec)
注意:以上操作完成了主从复制的配置,从节点可以正常备份主节点的数据,注意主节点不会备份从节点数据,若要双向备份需要采用互为主从的架构
3.3 测试
主节点创建数据库

从节点查看数据库是否更新

以上过程完成了数据库一主一从架构的配置
四、一主两从架构配置
4.1 新从机配置
上述配置不变,在原先一主一从架构中添加一个从节点
- 编辑配置文件并重启mysqld
bash
[root@mysql-node3 ~]# vim /etc/my.cnf
[mysqld]
datadir=/data/mysql
socket=/data/mysql/mysql.sock
symbolic-links=0
server-id=30
log-bin=mysql-bin
[root@mysql-node3 ~]# /etc/init.d/mysqld restart
- 数据同步
此时原先架构中,已经创建了新的数据库和表格并且填入了数据,此时新加入的从节点需要先手动进行数据同步
bash
# 主节点中导出有数据的数据库并复制给新的从节点
[root@mysql-node1 ~]# mysqldump -uroot -p123 doubledragon > doubledragon.sql
[root@mysql-node1 ~]# scp doubledragon.sql root@172.25.254.30:/roor/
# 从节点中导入数据
[root@mysql-node3 ~]# mysql -uroot -p123 -e "create database doubledragon;"
[root@mysql-node3 ~]# mysql -uroot -p123 doubledragon < doubledragon.sql
- 开启主从复制
bash
# 重新查询主节点master状态后再配置主从
mysql> CHANGE MASTER TO MASTER_HOST='172.25.254.10', MASTER_USER='dragon', MASTER_PASSWORD='123', MASTER_LOG_FILE='mysql-bin.000001', MASTER_LOG_POS=1251;
mysql> start slave;
mysql> start slave;
Query OK, 0 rows affected, 2 warnings (0.00 sec)
mysql> show slave status\G
*************************** 1. row ***************************
Slave_IO_State: Waiting for source to send event
Master_Host: 172.25.254.10
Master_User: dragon
Master_Port: 3306
Connect_Retry: 60
Master_Log_File: mysql-bin.000011
Read_Master_Log_Pos: 423
Relay_Log_File: mysql-node3-relay-bin.000005
Relay_Log_Pos: 600
Relay_Master_Log_File: mysql-bin.000011
Slave_IO_Running: Yes # 均为yes即可
Slave_SQL_Running: Yes # 为yes
Replicate_Do_DB:
Replicate_Ignore_DB:
Replicate_Do_Table:
Replicate_Ignore_Table:
Replicate_Wild_Do_Table:
Replicate_Wild_Ignore_Table:
Last_Errno: 0
Last_Error:
Skip_Counter: 0
Exec_Master_Log_Pos: 423
Relay_Log_Space: 1725
Until_Condition: None
Until_Log_File:
Until_Log_Pos: 0
Master_SSL_Allowed: No
Master_SSL_CA_File:
Master_SSL_CA_Path:
Master_SSL_Cert:
Master_SSL_Cipher:
Master_SSL_Key:
Seconds_Behind_Master: 0
Master_SSL_Verify_Server_Cert: No
Last_IO_Errno: 0
Last_IO_Error:
Last_SQL_Errno: 0
Last_SQL_Error:
Replicate_Ignore_Server_Ids:
Master_Server_Id: 10
Master_UUID: b7633ffa-12b4-11f1-90ce-000c29d81805
Master_Info_File: mysql.slave_master_info
SQL_Delay: 0
SQL_Remaining_Delay: NULL
Slave_SQL_Running_State: Replica has read all relay log; waiting for more updates
Master_Retry_Count: 10
Master_Bind:
Last_IO_Error_Timestamp:
Last_SQL_Error_Timestamp:
Master_SSL_Crl:
Master_SSL_Crlpath:
Retrieved_Gtid_Set: b7633ffa-12b4-11f1-90ce-000c29d81805:1-4
Executed_Gtid_Set: 00edb57b-12b8-11f1-a822-000c29d050f7:1-8,
b7633ffa-12b4-11f1-90ce-000c29d81805:1-4
Auto_Position: 1
Replicate_Rewrite_DB:
Channel_Name:
Master_TLS_Version:
Master_public_key_path:
Get_master_public_key: 0
Network_Namespace:
1 row in set, 1 warning (0.00 sec)
以上流程完成了数据库一主两从架构的配置
4.2 测试
主库再创建新的数据库

从库查看

可见数据成功同步,至此一主两从架构配置完毕