2020年5月28日星期四

MySQL所有的主从同步架构搭建方式

MySQL所有的主从同步架构搭建方式


致力于一条龙式的为您解决问题

目录

  • 一.前言
  • 二.关于MySQL主从同步
  • 三.部署规划
    • 3.1 服务器规划
    • 3.2 数据库目录规划
  • 四.准备工具
  • 五.四台机器上使用通用二进制包安装MySQL(以node7为例)
    • 5.1 上传MySQL通用二进制安装包到node7的/usr/local/src目录下
    • 5.2 解压MySQL到指定目录并改名
    • 5.3 创建MySQL用户和用户组
    • 5.4 配置MySQL的bin目录到PATH路径
    • 5.5 创建MySQL数据存放目录
    • 5.6 配置MySQL配置文件
    • 5.7 初始化MySQL数据库
    • 5.8 生成ssl(可选)
    • 5.9 配置MySQL启动项并设置开机自启动
      • 5.9.1 centos6版本
      • 5.9.2 centos7版本
    • 5.10 启动MySQL
    • 5.11 进行MySQL安全初始化(可选)
    • 5.12 修改密码,给用户赋权限(根据自己情况赋权限)
    • 5.13 导入时区信息到MySQL库
    • 5.14 查看MySQL版本信息
    • 5.15 如果防火墙开着,则需要开放3306端口
    • 5.16 利用logrotate对MySQL日志进行轮转(日志自动备份切割)
  • 六.MySQL主从同步之一主多从架构
    • 6.1 服务器规划
    • 6.2 主从同步的原理
    • 6.3 部署MySQL主从同步之一主多从
      • 6.3.1 配置主数据库服务器node7
        • 6.3.1.1 创建需要同步的数据库及其表
        • 6.3.1.2 修改MySQL配置文件
        • 6.3.1.3 主库给从库授予replication权限
        • 6.3.1.4 备份主库需要从库同步的数据库hotdata
      • 6.3.2 配置从数据库服务器node8
        • 6.3.2.1 检查数据库版本
        • 6.3.2.2 测试连接到主服务器是否成功
        • 6.3.2.3 导入hotdata数据库,和主数据库保持一致
        • 6.3.2.4 修改配置文件
        • 6.3.2.5 从库设置slave复制主库数据
      • 6.3.3 配置从数据库服务器node9
      • 6.3.4 在主服务器上查看状态
      • 6.3.5 插入数据测试主从同步
      • 6.3.6 彻底取消主从同步
    • 6.4 总结
  • 七.MySQL主从同步之主主双向同步架构
    • 7.1 服务器规划
    • 7.2 主从同步的原理
    • 7.3 部署MySQL主从同步之主主双向同步
      • 7.3.1 配置数据库服务器node7
        • 7.3.1.1 创建需要同步的数据库及其表
        • 7.3.1.2 修改MySQL配置文件
        • 7.3.1.3 给node8授予replication的权限
      • 7.3.2 配置数据库服务器node8
        • 7.3.2.1 创建需要同步的数据库及其表
        • 7.3.2.2 修改MySQL配置文件
        • 7.3.2.3 测试从账号slave能否登陆node7
        • 7.3.2.4 给node7赋予replication权限,并设置node8复制node7
      • 7.3.3 配置数据库服务器node7
        • 7.3.3.1 测试从账号slave能否登陆node8
        • 7.3.3.2 设置node7复制node8
      • 7.3.4 插入数据测试主从是否同步
        • 7.3.4.1 在node7上插入数据,查看node8 上有没有同步数据
        • 7.3.4.2 在node8上插入数据,查看node7 上有没有同步数据
      • 7.3.5 彻底取消主从同步
    • 7.4 总结
  • 八.MySQL主从同步之M-S-S架构
    • 8.1 服务器规划
    • 8.2 主从同步的原理
    • 8.3 部署MySQL主从同步之M-S-S
      • 8.3.1 配置主数据库服务器node7
        • 8.3.1.1 创建需要同步的数据库及其表
        • 8.3.1.2 授予node8 replication的权限
        • 8.3.1.3 修改配置文件并重启
      • 8.3.2 配置slave中继node8
        • 8.3.2.1 创建需要同步的数据库及其表
        • 8.3.2.2 修改配置文件并重启
        • 8.3.2.3 授权node8复制node7,并授予node9 replication的权限
      • 8.3.3 配置从服务器node9
        • 8.3.3.1 创建需要同步的数据库及其表
        • 8.3.3.2 修改配置文件并重启
        • 8.3.3.3 指定node8为node9的主
      • 8.3.4 插入数据测试
    • 8.4 总结
  • 九.MySQL主从同步之多主多从架构
    • 9.1 服务器规划
    • 9.2 MySQL多主多从架构图
    • 9.3 主从同步的原理
    • 9.4 部署MySQL主从同步之双主双从
      • 9.4.1 配置主数据库服务器node6
        • 9.4.1.1 创建需要同步的数据库及其表
        • 9.4.1.2 修改node6的MySQL配置文件
        • 9.4.1.3 node6创建复制账号并授权给node7和node8
      • 9.4.2 配置主数据库服务器node7
        • 9.4.2.1 创建需要同步的数据库及其表
        • 9.4.2.2 修改node7的MySQL配置文件
        • 9.4.2.3 node7创建复制账号并授权给node6和node9
      • 9.4.3 配置从数据库服务器node8
        • 9.4.3.1 创建需要同步的数据库及其表
        • 9.4.3.2 修改node8的MySQL配置文件
      • 9.4.4 配置从数据库服务器node9
        • 9.4.4.1 创建需要同步的数据库及其表
        • 9.4.4.2 修改node9的MySQL配置文件
      • 9.4.5 在slave上配置master(所有节点)
      • 9.4.6 启动slave,让四台MySQL进入主从复制状态
      • 9.4.7 测试验证双主双从
    • 9.5 总结
  • 十.参考资料

一.前言

​ 本文将指导搭建所有的MySQL主从同步架构方案:

  • ​ 一主多从架构
  • ​ 主主双向同步架构
  • ​ M-S-S三级级联同步架构
  • ​ 多主多从架构

二.关于MySQL主从同步

​ MySQL主从同步是构建大型,高性能应用的基础,MySQL主从同步可以实现在从服务器可以执行查询工作(即我们常说的读功能),降低主服务器压力(主库写,从库读,降压),在从主服务器进行备份,避免备份期间影响主服务器服务(确保数据安全),当主服务器出现问题时,可以切换到从服务器(提升性能)。

三.部署规划

3.1 服务器规划

服务器操作系统版本CPU架构MySQL版本
node6CentOS Linux release 7.4.1708x86_645.7.26
node7CentOS Linux release 7.4.1708x86_645.7.26
node8CentOS Linux release 7.4.1708x86_645.7.26
node9CentOS Linux release 7.4.1708x86_645.7.26

3.2 数据库目录规划

文件类型文件部署位置
数据目录datadir/data/data(/data目录请确保足够大)
配置文件my.cnf/etc/my.cnf
错误日志log-error/data/log/mysql_error.log
二进制日志log-bin/data/binlogs/mysql-bin(用于数据库恢复和主从复制,以及审计(audit)操作)
慢查询日志slow_query_log_file/data/log/mysql_slow_query.log
套接字文件socket/data/run/mysql.sock
进程ID文件mysql.pid/data/run/mysql.pid

四.准备工具

1.MySQL通用二进制包:mysql-5.7.26-linux-glibc2.12-x86_64.tar.gz

下载地址:https://dev.mysql.com/downloads/mysql/5.7.html#downloads

1575168018572

五.四台机器上使用通用二进制包安装MySQL(以node7为例)

5.1 上传MySQL通用二进制安装包到node7的/usr/local/src目录下

[root@node7 src]# pwd/usr/local/src[root@node7 src]# lsmysql-5.7.26-linux-glibc2.12-x86_64.tar.gz

5.2 解压MySQL到指定目录并改名

[root@node7 src]# tar -zxf mysql-5.7.26-linux-glibc2.12-x86_64.tar.gz -C /usr/local/[root@node7 src]# cd /usr/local/[root@node7 local]# lsbin etc games include lib lib64 libexec mysql-5.7.26-linux-glibc2.12-x86_64 sbin share src[root@node7 local]# mv mysql-5.7.26-linux-glibc2.12-x86_64 mysql[root@node7 local]# lsbin etc games include lib lib64 libexec mysql sbin share src

5.3 创建MySQL用户和用户组

[root@node7 local]# groupadd -g 1111 mysql[root@node7 local]# useradd -g mysql -u 1111 -s /sbin/nologin mysql[root@node7 local]# id mysql #查看用户信息uid=1111(mysql) gid=1111(mysql) groups=1111(mysql)

5.4 配置MySQL的bin目录到PATH路径

[root@node7 local]# echo "export PATH=$PATH:/usr/local/mysql/bin" >> /etc/profile[root@node7 local]# source /etc/profile[root@node7 local]# mysql #输入MySQL之后双击tab键,即可列出候选MySQL命令mysql      mysql_client_test_embedded mysqld-debug    mysqldumpslow    mysql_plugin    mysqlslap     mysql_upgrademysqladmin     mysql_config    mysqld_multi    mysql_embedded    mysqlpump     mysql_ssl_rsa_setup   mysqlxtestmysqlbinlog     mysql_config_editor   mysqld_safe     mysqlimport     mysql_secure_installation mysqltest_embedded   mysqlcheck     mysqld      mysqldump     mysql_install_db   mysqlshow     mysql_tzinfo_to_sql

5.5 创建MySQL数据存放目录

[root@node7 ~]# mkdir -p /data/{data,log,binlogs,run}[root@node7 ~]# tree /data #如果没有tree命令,则yum -y install tree安装/data├── binlogs├── data├── log└── run4 directories, 0 files[root@node7 ~]# chown -R mysql:mysql /data[root@node7 ~]# ll /data/total 0drwxr-xr-x 2 mysql mysql 6 Dec 3 11:07 binlogsdrwxr-xr-x 2 mysql mysql 6 Dec 3 11:07 datadrwxr-xr-x 2 mysql mysql 6 Dec 3 11:07 logdrwxr-xr-x 2 mysql mysql 6 Dec 3 11:07 run

5.6 配置MySQL配置文件

[root@node7 mysql]# rm -rf /etc/my.cnf[root@node7 mysql]# touch /etc/my.cnf#my.cnf配置文件详解,请查看我上一篇blog的#https://www.cnblogs.com/renshengdezheli/p/11913248.html的"MySQL配置文件优化参考"[root@node7 mysql]# cat /etc/my.cnf[client]port=3306socket=/data/run/mysql.sock[mysqld]port=3306socket=/data/run/mysql.sockpid_file=/data/run/mysql.piddatadir=/data/datadefault_storage_engine=InnoDBmax_allowed_packet=512Mmax_connections=2048open_files_limit=65535skip-name-resolvelower_case_table_names=1character-set-server=utf8mb4collation-server=utf8mb4_unicode_ciinit_connect='SET NAMES utf8mb4'innodb_buffer_pool_size=1024Minnodb_log_file_size=2048Minnodb_file_per_table=1innodb_flush_log_at_trx_commit=0key_buffer_size=64Mlog-error=/data/log/mysql_error.loglog-bin=/data/binlogs/mysql-binslow_query_log=1slow_query_log_file=/data/log/mysql_slow_query.loglong_query_time=5tmp_table_size=32Mmax_heap_table_size=32Mquery_cache_type=0query_cache_size=0server-id=1

5.7 初始化MySQL数据库

[root@node7 mysql]# mysqld --initialize --user=mysql --basedir=/usr/local/mysql --datadir=/data/data[root@node7 mysql]# echo $?0[root@node7 mysql]# grep 'temporary password' /data/log/mysql_error.log #查看MySQL初始化密码2019-12-03T03:47:42.639938Z 1 [Note] A temporary password is generated for root@localhost: lhrh>J,p<8gw

5.8 生成ssl(可选)

#关于MySQL开启ssl查看https://www.cnblogs.com/mysql-dba/p/7061300.html[root@node7 mysql]# mysql_ssl_rsa_setup --basedir=/usr/local/mysql --datadir=/data/dataGenerating a 2048 bit RSA private key......................................+++.+++writing new private key to 'ca-key.pem'-----Generating a 2048 bit RSA private key....................................+++............................+++writing new private key to 'server-key.pem'-----Generating a 2048 bit RSA private key.....................................................................................+++..............................................+++writing new private key to 'client-key.pem'-----#执行完成之后,会有在datadir目录生成*.pem文件[root@node7 mysql]# ls /data/data/auto.cnf client-cert.pem ibdata1  mysql    public_key.pem sysca-key.pem client-key.pem ib_logfile0 performance_schema server-cert.pemca.pem  ib_buffer_pool ib_logfile1 private_key.pem  server-key.pem

5.9 配置MySQL启动项并设置开机自启动

5.9.1 centos6版本

cd /usr/local/mysqlcp support-files/mysql.server /etc/init.d/mysql.serverchkconfig --add mysql.serverchkconfig mysql.server onchkconfig --list

5.9.2 centos7版本

[root@node7 system]# cd /usr/lib/systemd/system[root@node7 system]# touch mysqld.service [root@node7 system]# vim mysqld.service [root@node7 system]# cat mysqld.service # Copyright (c) 2015, 2016, Oracle and/or its affiliates. All rights reserved.## This program is free software; you can redistribute it and/or modify# it under the terms of the GNU General Public License as published by# the Free Software Foundation; version 2 of the License.## This program is distributed in the hope that it will be useful,# but WITHOUT ANY WARRANTY; without even the implied warranty of# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the# GNU General Public License for more details.## You should have received a copy of the GNU General Public License# along with this program; if not, write to the Free Software# Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA## systemd service file for MySQL forking server#[Unit]Description=MySQL ServerDocumentation=man:mysqld(5.7)Documentation=http://dev.mysql.com/doc/refman/en/using-systemd.htmlAfter=network.targetAfter=syslog.target[Install]WantedBy=multi-user.target[Service]User=mysqlGroup=mysqlType=forkingPIDFile=/data/run/mysql.pid# Disable service start and stop timeout logic of systemd for mysqld service.TimeoutSec=0# Execute pre and post scripts as rootPermissionsStartOnly=true# Needed to create system tables#ExecStartPre=/usr/bin/mysqld_pre_systemd# Start main serviceExecStart=/usr/local/mysql/bin/mysqld --daemonize --pid-file=/data/run/mysql.pid $MYSQLD_OPTS# Use this to switch malloc implementationEnvironmentFile=-/etc/sysconfig/mysql# Sets open_files_limitLimitNOFILE = 65535Restart=on-failureRestartPreventExitStatus=1PrivateTmp=false[root@node7 system]# systemctl daemon-reload #重新加载服务配置文件[root@node7 system]# systemctl enable mysqld #设置MySQL开机自启动Created symlink from /etc/systemd/system/multi-user.target.wants/mysqld.service to /usr/lib/systemd/system/mysqld.service.[root@node7 system]# systemctl is-enabled mysqld #查看MySQL开机自启动是否设置成功enabled

5.10 启动MySQL

[root@node7 system]# systemctl start mysqld[root@node7 system]# systemctl status mysqld #查看MySQL启动状态● mysqld.service - MySQL Server Loaded: loaded (/usr/lib/systemd/system/mysqld.service; enabled; vendor preset: disabled) Active: active (running) since Tue 2019-12-03 14:42:14 CST; 9s ago  Docs: man:mysqld(5.7)   Process: 2905 ExecStart=/usr/local/mysql/bin/mysqld --daemonize --pid-file=/data/run/mysql.pid $MYSQLD_OPTS (code=exited, status=0/SUCCESS) Main PID: 2907 (mysqld) CGroup: /system.slice/mysqld.service   └─2907 /usr/local/mysql/bin/mysqld --daemonize --pid-file=/data/run/mysql.pidDec 03 14:42:13 node7 systemd[1]: Starting MySQL Server...Dec 03 14:42:14 node7 systemd[1]: Started MySQL Server.[root@node7 system]# ps -ef | grep mysql   #查看MySQL进程mysql  2907  1 2 14:42 ?  00:00:00 /usr/local/mysql/bin/mysqld --daemonize --pid-file=/data/run/mysql.pidroot  2942 2576 0 14:42 pts/0 00:00:00 grep --color=auto mysql

5.11 进行MySQL安全初始化(可选)

[root@node7 system]# mysql_secure_installation Securing the MySQL server deployment.Enter password for user root: #这里输入MySQL初始化时生成的密码(grep 'temporary password' /data/log/mysql_error.log)The existing password for the user account root has expired. Please set a new password.New password: #输入新密码Re-enter new password: VALIDATE PASSWORD PLUGIN can be used to test passwordsand improve security. It checks the strength of passwordand allows the users to set only those passwords which aresecure enough. Would you like to setup VALIDATE PASSWORD plugin?Press y|Y for Yes, any other key for No: n #y安装MySQL密码插件Using existing password for root.Change the password for root ? ((Press y|Y for Yes, any other key for No) : n ... skipping.By default, a MySQL installation has an anonymous user,allowing anyone to log into MySQL without having to havea user account created for them. This is intended only fortesting, and to make the installation go a bit smoother.You should remove them before moving into a productionenvironment.Remove anonymous users? (Press y|Y for Yes, any other key for No) : y #y移除匿名用户Success.Normally, root should only be allowed to connect from'localhost'. This ensures that someone cannot guess atthe root password from the network.Disallow root login remotely? (Press y|Y for Yes, any other key for No) : n #是否允许root远程登录 ... skipping.By default, MySQL comes with a database named 'test' thatanyone can access. This is also intended only for testing,and should be removed before moving into a productionenvironment.Remove test database and access to it? (Press y|Y for Yes, any other key for No) : y #是否移除test数据库 - Dropping test database...Success. - Removing privileges on test database...Success.Reloading the privilege tables will ensure that all changesmade so far will take effect immediately.Reload privilege tables now? (Press y|Y for Yes, any other key for No) : y #刷新权限表Success.All done!

5.12 修改密码,给用户赋权限(根据自己情况赋权限)

[root@node7 ~]# mysql -uroot -p123456mysql> SET PASSWORD = PASSWORD('123456');#修改root密码为123456,如果提示ERROR 1819 (HY000): Your password does not satisfy the current policy requirements,则说明密码设置太简单,如果想设置123456这样的简单密码,可在SQL中执行:	#mysql> set global validate_password_policy=0;	#mysql> set global validate_password_length=1;	#这样再次执行SET PASSWORD = PASSWORD('123456')就可成功。Query OK, 0 rows affected, 1 warning (0.01 sec)mysql> UPDATE mysql.user SET authentication_string =PASSWORD('123456') WHERE User='mysql'; #修改MySQL的mysql用户的密码为123456Query OK, 0 rows affected, 1 warning (0.00 sec)Rows matched: 0 Changed: 0 Warnings: 1mysql> GRANT ALL PRIVILEGES ON *.* TO mysql@localhost IDENTIFIED BY '123456' WITH GRANT OPTION; Query OK, 0 rows affected, 2 warnings (0.00 sec)mysql> GRANT ALL PRIVILEGES ON *.* TO mysql@"%" IDENTIFIED BY '123456' WITH GRANT OPTION; #赋予mysql用户可以在任何机器上登录,并拥有所有表的所有权限Query OK, 0 rows affected, 1 warning (0.00 sec)mysql> GRANT ALL PRIVILEGES ON *.* TO root@localhost IDENTIFIED BY '123456' WITH GRANT OPTION;Query OK, 0 rows affected, 2 warnings (0.00 sec)mysql> GRANT ALL PRIVILEGES ON *.* TO root@"%" IDENTIFIED BY '123456' WITH GRANT OPTION;Query OK, 0 rows affected, 1 warning (0.07 sec)mysql> FLUSH PRIVILEGES ; #刷新权限,让修改立即生效Query OK, 0 rows affected (0.00 sec)mysql> exit;Bye----------------------------------------------------------------------------------------------------------------------------------------------------------------------------#以下是为MySQL赋权限的介绍mysql> grant 权限1,权限2,…权限n on 数据库名称.表名称 to 用户名@用户地址 identified by '连接口令';权限1,权限2,…权限n代表select,insert,update,delete,create,drop,index,alter,grant,references,reload,shutdown,process,file等14个权限。当权限1,权限2,…权限n被all privileges或者all代替,表示赋予用户全部权限。当数据库名称.表名称被*.*代替,表示赋予用户操作服务器上所有数据库所有表的权限。用户地址可以是localhost,也可以是ip地址、机器名字、域名。也可以用'%'表示从任何地址连接。'连接口令'不能为空,否则创建失败。比如:mysql>grant select,insert,update,delete,create,drop on vtdc.employee to joe@10.163.225.87 identified by '123′;给来自10.163.225.87的用户joe分配可对数据库vtdc的employee表进行select,insert,update,delete,create,drop等操作的权限,并设定口令为123。 mysql>grant all privileges on vtdc.* to joe@10.163.225.87 identified by '123′;给来自10.163.225.87的用户joe分配可对数据库vtdc所有表进行所有操作的权限,并设定口令为123。----------------------------------------------------------------------------------------------------------------------------------------------------------------------------

5.13 导入时区信息到MySQL库

[root@node7 system]# mysql_tzinfo_to_sql /usr/share/zoneinfo | mysql -uroot -p123456 mysql#执行上述操作之后,time_zone,time_zone_leap_second,time_zone_name,time_zone_transition ,time_zone_transition_type表就有时区数据了[root@node7 system]# mysql -uroot -p123456 mysqlmysql> show tables;+---------------------------+| Tables_in_mysql   |+---------------------------+| columns_priv    || db      || engine_cost    || event      || func      || general_log    || gtid_executed    || help_category    || help_keyword    || help_relation    || help_topic    || innodb_index_stats  || innodb_table_stats  || ndb_binlog_index   || plugin     || proc      || procs_priv    || proxies_priv    || server_cost    || servers     || slave_master_info   || slave_relay_log_info  || slave_worker_info   || slow_log     || tables_priv    || time_zone     || time_zone_leap_second  || time_zone_name   || time_zone_transition  || time_zone_transition_type || user      |+---------------------------+31 rows in set (0.00 sec)

5.14 查看MySQL版本信息

[root@node7 system]# mysql -Vmysql Ver 14.14 Distrib 5.7.26, for linux-glibc2.12 (x86_64) using EditLine wrapper[root@node7 system]# mysqladmin version -uroot -p123456mysqladmin: [Warning] Using a password on the command line interface can be insecure.mysqladmin Ver 8.42 Distrib 5.7.26, for linux-glibc2.12 on x86_64Copyright (c) 2000, 2019, Oracle and/or its affiliates. All rights reserved.Oracle is a registered trademark of Oracle Corporation and/or itsaffiliates. Other names may be trademarks of their respectiveowners.Server version		5.7.26-logProtocol version	10Connection		Localhost via UNIX socketUNIX socket		/data/run/mysql.sockUptime:			31 min 53 secThreads: 1 Questions: 8855 Slow queries: 0 Opens: 214 Flush tables: 1 Open tables: 203 Queries per second avg: 4.628

5.15 如果防火墙开着,则需要开放3306端口

[root@node7 system]# systemctl status firewalld● firewalld.service - firewalld - dynamic firewall daemon Loaded: loaded (/usr/lib/systemd/system/firewalld.service; disabled; vendor preset: enabled) Active: active (running) since Tue 2019-12-03 15:22:18 CST; 3s ago  Docs: man:firewalld(1) Main PID: 3343 (firewalld) CGroup: /system.slice/firewalld.service   └─3343 /usr/bin/python -Es /usr/sbin/firewalld --nofork --nopidDec 03 15:22:17 node7 systemd[1]: Starting firewalld - dynamic firewall daemon...Dec 03 15:22:18 node7 systemd[1]: Started firewalld - dynamic firewall daemon.Dec 03 15:22:18 node7 firewalld[3343]: WARNING: ICMP type 'beyond-scope' is not supported by the kernel for ipv6.Dec 03 15:22:18 node7 firewalld[3343]: WARNING: beyond-scope: INVALID_ICMPTYPE: No supported ICMP type., ignoring...-time.Dec 03 15:22:18 node7 firewalld[3343]: WARNING: ICMP type 'failed-policy' is not supported by the kernel for ipv6.Dec 03 15:22:18 node7 firewalld[3343]: WARNING: failed-policy: INVALID_ICMPTYPE: No supported ICMP type., ignorin...-time.Dec 03 15:22:18 node7 firewalld[3343]: WARNING: ICMP type 'reject-route' is not supported by the kernel for ipv6.Dec 03 15:22:18 node7 firewalld[3343]: WARNING: reject-route: INVALID_ICMPTYPE: No supported ICMP type., ignoring...-time.Hint: Some lines were ellipsized, use -l to show in full.#添加防火墙规则[root@node7 system]# firewall-cmd --permanent --zone=public --add-port=3306/tcpsuccess#重新加载防火墙规则[root@node7 system]# firewall-cmd --reloadsuccess#检查规则是否设置生效[root@node7 system]# firewall-cmd --zone=public --query-port=3306/tcpyes#列出防火墙所有开放的端口[root@node7 system]# firewall-cmd --list-allpublic (active) target: default icmp-block-inversion: no interfaces: ens33 sources: services: ssh dhcpv6-client ports: 3306/tcp protocols: masquerade: no forward-ports: source-ports: icmp-blocks: rich rules: 

5.16 利用logrotate对MySQL日志进行轮转(日志自动备份切割)

#logrotate配置详解请查看:https://www.linuxidc.com/Linux/2019-02/157099.htm[root@node7 ~]# touch /root/.my.cnf[root@node7 ~]# vim /root/.my.cnf [root@node7 ~]# cat /root/.my.cnf [mysqladmin] password=123456user=root[root@node7 ~]# chmod 600 /root/.my.cnf [root@node7 ~]# cp /usr/local/mysql/support-files/mysql-log-rotate /etc/logrotate.d/[root@node7 ~]# chmod 644 /etc/logrotate.d/mysql-log-rotate [root@node7 ~]# vim /etc/logrotate.d/mysql-log-rotate [root@node7 ~]# cat /etc/logrotate.d/mysql-log-rotate # The log file name and location can be set in# /etc/my.cnf by setting the "log-error" option# in either [mysqld] or [mysqld_safe] section as# follows:## [mysqld]# log-error=/usr/local/mysql/data/mysqld.log## In case the root user has a password, then you# have to create a /root/.my.cnf configuration file# with the following content:## [mysqladmin]# password = <secret> # user= root## where "<secret>" is the password. ## ATTENTION: The /root/.my.cnf file should be readable# _ONLY_ by root !/data/log/mysql_*.log {  # create 600 mysql mysql  notifempty #当日志文件为空时,不进行轮转  daily #默认每一天执行一次rotate轮转工作  rotate 52 #保留多少个日志文件(轮转几次).默认保留四个.就是指定日志文件删除之前轮转的次数,0 指没有备份,此处表示保留52天的日志  missingok #如果日志文件丢失,不要显示错误  compress #通过gzip 压缩转储以后的日志 postrotate #执行的指令	# just if mysqld is really running	if test -x /usr/local/mysql/bin/mysqladmin && \	 /usr/local/mysql/bin/mysqladmin ping &>/dev/null	then	 /usr/local/mysql/bin/mysqladmin flush-logs	fi endscript}[root@node7 ~]# [root@node7 ~]# logrotate -fv /etc/logrotate.d/mysql-log-rotate #强制进行日志轮转reading config file /etc/logrotate.d/mysql-log-rotateAllocating hash table for state file, size 15360 BHandling 1 logsrotating pattern: /data/log/mysql_*.log forced from command line (52 rotations)empty log files are not rotated, old logs are removedconsidering log /data/log/mysql_error.log log needs rotatingconsidering log /data/log/mysql_slow_query.log log needs rotatingrotating log /data/log/mysql_error.log, log->rotateCount is 52dateext suffix '-20191203'glob pattern '-[0-9][0-9][0-9][0-9][0-9][0-9][0-9][0-9]'renaming /data/log/mysql_error.log.52.gz to /data/log/mysql_error.log.53.gz (t -- won't try to dispose of it.................renaming /data/log/mysql_slow_query.log to /data/log/mysql_slow_query.log.1running postrotate scriptcompressing log with: /bin/gzip[root@node7 ~]# [root@node7 ~]# echo $?0#此时查看日志目录,发现日志已经进行轮转,并压缩[root@node7 ~]# ls /data/log/mysql_error.log mysql_error.log.1.gz mysql_slow_query.log mysql_slow_query.log.1.gz

自此,node7上MySQL安装完毕,node6,node8,node9上的MySQL也按照此方法安装。

安装MySQL是进行主从同步,读写分离,分表分库配置的基础,只有安装了MySQL才能进行接下来的操作。

六.MySQL主从同步之一主多从架构

6.1 服务器规划

主机名IP操作系统版本MySQL版本角色
node7192.168.110.188CentOS 7.4.17085.7.26master(主)
node8192.168.110.186CentOS 7.4.17085.7.26slave(从)
node9192.168.110.187CentOS 7.4.17085.7.26slave(从)

6.2 主从同步的原理

​ master将改变记录到二进制日志(binary log)中,slave将master的binary log events拷贝到它的中继日志(relay log),slave重做中继日志中的事件,修改salve上的数据。

6.3 部署MySQL主从同步之一主多从

6.3.1 配置主数据库服务器node7

6.3.1.1 创建需要同步的数据库及其表

[root@node7 ~]# mysql -uroot -p123456mysql> create database hotdata;  #创建热点数据库Query OK, 1 row affected (0.70 sec)mysql> use hotdata;Database changed#创建顾客表mysql> create table customers(cust_id int,cust_name varchar(30),cust_address varchar(50),cust_city varchar(30),cust_state varchar(50),cust_email varchar(30),cust_country varchar(50));Query OK, 0 rows affected (0.44 sec)mysql> desc customers; #查看表结构+--------------+-------------+------+-----+---------+-------+| Field  | Type  | Null | Key | Default | Extra |+--------------+-------------+------+-----+---------+-------+| cust_id  | int(11)  | YES |  | NULL |  || cust_name | varchar(30) | YES |  | NULL |  || cust_address | varchar(50) | YES |  | NULL |  || cust_city | varchar(30) | YES |  | NULL |  || cust_state | varchar(50) | YES |  | NULL |  || cust_email | varchar(30) | YES |  | NULL |  || cust_country | varchar(50) | YES |  | NULL |  |+--------------+-------------+------+-----+---------+-------+7 rows in set (0.36 sec)mysql> exitBye

6.3.1.2 修改MySQL配置文件

#先关闭数据库再修改MySQL配置文件[root@node7 ~]# systemctl stop mysqld[root@node7 ~]# systemctl status mysqld● mysqld.service - MySQL Server Loaded: loaded (/usr/lib/systemd/system/mysqld.service; enabled; vendor preset: disabled) Active: inactive (dead) since Thu 2019-12-05 10:59:38 CST; 8s ago  Docs: man:mysqld(5.7)   Process: 6777 ExecStart=/usr/local/mysql/bin/mysqld --daemonize --pid-file=/data/run/mysql.pid $MYSQLD_OPTS (code=exited, status=0/SUCCESS) Main PID: 6779 (code=exited, status=0/SUCCESS)Dec 05 10:35:44 node7 systemd[1]: Starting MySQL Server...Dec 05 10:36:07 node7 systemd[1]: Started MySQL Server.Dec 05 10:59:36 node7 systemd[1]: Stopping MySQL Server...Dec 05 10:59:38 node7 systemd[1]: Stopped MySQL Server.#修改好的配置文件如下,主从同步相关的配置都放在"#mysql replication"下面[root@node7 ~]# vim /etc/my.cnf[root@node7 ~]# cat /etc/my.cnf[client]port=3306socket=/data/run/mysql.sock[mysqld]port=3306socket=/data/run/mysql.sockpid_file=/data/run/mysql.piddatadir=/data/datadefault_storage_engine=InnoDBmax_allowed_packet=512Mmax_connections=2048open_files_limit=65535skip-name-resolvelower_case_table_names=1character-set-server=utf8mb4collation-server=utf8mb4_unicode_ciinit_connect='SET NAMES utf8mb4'innodb_buffer_pool_size=1024Minnodb_log_file_size=2048Minnodb_file_per_table=1innodb_flush_log_at_trx_commit=0key_buffer_size=64Mlog-error=/data/log/mysql_error.logslow_query_log=1slow_query_log_file=/data/log/mysql_slow_query.loglong_query_time=5tmp_table_size=32Mmax_heap_table_size=32Mquery_cache_type=0query_cache_size=0skip_ssl#mysql replication,主从同步配置#logbin参数启用二进制日志,并把二进制日志放在/data/binlogs目录下log-bin=/data/binlogs/mysql-bin #数据库标志ID,唯一server-id=1#binlog-do-db可以被从服务器复制的库binlog-do-db=hotdata#binlog-ignore-db不可以被从服务器复制的库binlog-ignore-db=mysql[root@node7 ~]# systemctl restart mysqld #重启MySQL数据库

6.3.1.3 主库给从库授予replication权限

[root@node7 ~]# mysql -uroot -p123456#授予node8从库replication权限mysql> grant replication slave on *.* to slave@192.168.110.186 identified by "123456";Query OK, 0 rows affected, 1 warning (0.11 sec)#授予node9从库replication权限mysql> grant replication slave on *.* to slave@192.168.110.187 identified by "123456";Query OK, 0 rows affected, 1 warning (0.01 sec)#刷新权限mysql> flush privileges;Query OK, 0 rows affected (0.00 sec)#查看master状态信息mysql> show master status;+------------------+----------+--------------+------------------+-------------------+| File    | Position | Binlog_Do_DB | Binlog_Ignore_DB | Executed_Gtid_Set |+------------------+----------+--------------+------------------+-------------------+| mysql-bin.000012 |  902 | hotdata  | mysql   |     |+------------------+----------+--------------+------------------+-------------------+1 row in set (0.00 sec)mysql> exitBye#查看二进制日志[root@node7 ~]# ll /data/binlogs/total 2896-rw-r----- 1 mysql mysql  177 Dec 3 11:47 mysql-bin.000001-rw-r----- 1 mysql mysql 2915818 Dec 3 16:38 mysql-bin.000002-rw-r----- 1 mysql mysql  201 Dec 3 16:38 mysql-bin.000003-rw-r----- 1 mysql mysql  177 Dec 3 17:09 mysql-bin.000004-rw-r----- 1 mysql mysql  177 Dec 3 17:14 mysql-bin.000005-rw-r----- 1 mysql mysql  177 Dec 3 17:25 mysql-bin.000006-rw-r----- 1 mysql mysql 1220 Dec 4 03:12 mysql-bin.000007-rw-r----- 1 mysql mysql  201 Dec 4 03:12 mysql-bin.000008-rw-r----- 1 mysql mysql  177 Dec 4 10:49 mysql-bin.000009-rw-r----- 1 mysql mysql 1743 Dec 5 10:35 mysql-bin.000010-rw-r----- 1 mysql mysql  665 Dec 5 10:59 mysql-bin.000011-rw-r----- 1 mysql mysql  902 Dec 5 11:47 mysql-bin.000012-rw-r----- 1 mysql mysql  372 Dec 5 11:40 mysql-bin.index[root@node7 ~]# mysql -uroot -p123456##查看二进制日志事件mysql> show binlog events\G*************************** 1. row *************************** Log_name: mysql-bin.000001  Pos: 4 Event_type: Format_desc Server_id: 1End_log_pos: 123  Info: Server ver: 5.7.26-log, Binlog ver: 4*************************** 2. row *************************** Log_name: mysql-bin.000001  Pos: 123 Event_type: Previous_gtids Server_id: 1End_log_pos: 154  Info: *************************** 3. row *************************** Log_name: mysql-bin.000001  Pos: 154 Event_type: Stop Server_id: 1End_log_pos: 177  Info: 3 rows in set (0.00 sec)mysql> exitBye

6.3.1.4 备份主库需要从库同步的数据库hotdata

#备份数据库hotdata[root@node7 ~]# mysqldump -uroot -p123456 hotdata >hotdata.sqlmysqldump: [Warning] Using a password on the command line interface can be insecure.#给从库分发备份好的数据库[root@node7 ~]# scp hotdata.sql root@192.168.110.186:~/hotdata.sql          100% 2239 510.9KB/s 00:00 [root@node7 ~]# scp hotdata.sql root@192.168.110.187:~/hotdata.sql          100% 2239 382.8KB/s 00:00 

6.3.2 配置从数据库服务器node8

6.3.2.1 检查数据库版本

#主从数据库版本不一致的话会出现问题[root@node8 ~]# mysql -uroot -p123456mysql> show variables like "%version%";+-------------------------+------------------------------+| Variable_name   | Value      |+-------------------------+------------------------------+| innodb_version   | 5.7.26      || protocol_version  | 10       || slave_type_conversions |        || tls_version    | TLSv1,TLSv1.1    || version     | 5.7.26-log     || version_comment   | MySQL Community Server (GPL) || version_compile_machine | x86_64      || version_compile_os  | linux-glibc2.12    |+-------------------------+------------------------------+8 rows in set (0.01 sec)mysql> quitBye

6.3.2.2 测试连接到主服务器是否成功

[root@node8 ~]# mysql -uslave -p123456 -h 192.168.110.188#只有复制的权限, 是看不到其他库的。mysql> show databases;+--------------------+| Database   |+--------------------+| information_schema |+--------------------+1 row in set (0.00 sec)mysql> exitBye

6.3.2.3 导入hotdata数据库,和主数据库保持一致

[root@node8 ~]# mysql -uroot -p123456mysql> create database hotdata;Query OK, 1 row affected (0.00 sec)mysql> exitBye#导入hotdata表[root@node8 ~]# mysql -uroot -p123456 hotdata<hotdata.sql mysql: [Warning] Using a password on the command line interface can be insecure.

6.3.2.4 修改配置文件

[root@node8 ~]# systemctl stop mysqld[root@node8 ~]# vim /etc/my.cnf[root@node8 ~]# cat /etc/my.cnf[client]port=3306socket=/data/run/mysql.sock[mysqld]port=3306socket=/data/run/mysql.sockpid_file=/data/run/mysql.piddatadir=/data/datadefault_storage_engine=InnoDBmax_allowed_packet=512Mmax_connections=2048open_files_limit=65535skip-name-resolvelower_case_table_names=1character-set-server=utf8mb4collation-server=utf8mb4_unicode_ciinit_connect='SET NAMES utf8mb4'innodb_buffer_pool_size=1024Minnodb_log_file_size=2048Minnodb_file_per_table=1innodb_flush_log_at_trx_commit=0key_buffer_size=64Mlog-error=/data/log/mysql_error.logslow_query_log=1slow_query_log_file=/data/log/mysql_slow_query.loglong_query_time=5tmp_table_size=32Mmax_heap_table_size=32Mquery_cache_type=0query_cache_size=0#mysql replication配置#server-id必须唯一server-id=2#下面log-bin,binlog-do-db,binlog-ignore-db这三个参数都不是必须的log-bin=/data/binlogs/mysql-binbinlog-do-db=hotdatabinlog-ignore-db=mysql[root@node8 ~]# [root@node8 ~]# systemctl restart mysqld

6.3.2.5 从库设置slave复制主库数据

[root@node8 ~]# mysql -uroot -p123456mysql> stop slave; #停止slaveQuery OK, 0 rows affected, 1 warning (0.00 sec)mysql> change master to master_host='192.168.110.188',master_user='slave',master_password='123456';Query OK, 0 rows affected, 2 warnings (0.02 sec)#释义:#change master to #master_host='192.168.0.68',master_user='root',master_password='root',master_log_file='#mysql-bin.000004', master_log_pos=28125;#上面的master_log_file是在Master中show master status显示的File,而master_log_pos是在Master中#show master status显示的Position。#也可以通过show slave status查看配置信息,如果没有同步成功,比对show slave status中的position和#file是否和show master status中的对应。mysql> start slave; #启动slaveQuery OK, 0 rows affected (0.01 sec)#查看slave状态mysql> show slave status\G  *************************** 1. row ***************************    Slave_IO_State: Waiting for master to send event     Master_Host: 192.168.110.188     Master_User: slave     Master_Port: 3306    Connect_Retry: 60    Master_Log_File: mysql-bin.000012   Read_Master_Log_Pos: 902    Relay_Log_File: node8-relay-bin.000010    Relay_Log_Pos: 519  Relay_Master_Log_File: mysql-bin.000007    Slave_IO_Running: Yes   Slave_SQL_Running: No    Replicate_Do_DB:   Replicate_Ignore_DB:   Replicate_Do_Table:  Replicate_Ignore_Table:  Replicate_Wild_Do_Table: Replicate_Wild_Ignore_Table:     Last_Errno: 1062     Last_Error: Could not execute Update_rows event on table mysql.user; Duplicate entry '%-root' for key 'PRIMARY', Error_code: 1062; handler error HA_ERR_FOUND_DUPP_KEY; the event's master log mysql-bin.000007, end_log_pos 942     Skip_Counter: 0   Exec_Master_Log_Pos: 306    Relay_Log_Space: 7216    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: NULLMaster_SSL_Verify_Server_Cert: No    Last_IO_Errno: 0    Last_IO_Error:    Last_SQL_Errno: 1062    Last_SQL_Error: Could not execute Update_rows event on table mysql.user; Duplicate entry '%-root' for key 'PRIMARY', Error_code: 1062; handler error HA_ERR_FOUND_DUPP_KEY; the event's master log mysql-bin.000007, end_log_pos 942 Replicate_Ignore_Server_Ids:    Master_Server_Id: 1     Master_UUID: a8da7421-157f-11ea-b1bf-000c297c0226    Master_Info_File: /data/data/master.info     SQL_Delay: 0   SQL_Remaining_Delay: NULL  Slave_SQL_Running_State:   Master_Retry_Count: 86400     Master_Bind:  Last_IO_Error_Timestamp:  Last_SQL_Error_Timestamp: 191205 15:18:40    Master_SSL_Crl:   Master_SSL_Crlpath:   Retrieved_Gtid_Set:    Executed_Gtid_Set:     Auto_Position: 0   Replicate_Rewrite_DB:     Channel_Name:   Master_TLS_Version: 1 row in set (0.00 sec)#可以看到Last_Error报错了,是因为主键重复了,按照下面操作即可mysql> stop slave;Query OK, 0 rows affected (0.00 sec)mysql> SET GLOBAL sql_slave_skip_counter =1;Query OK, 0 rows affected (0.00 sec)mysql> start slave;Query OK, 0 rows affected (0.00 sec)#再次查看slave状态,如果Last_Error没报错,并且Slave_IO_Running和Slave_SQL_Running都为yes则说明#配置成功了#Slave_IO_Running :负责与主机的IO通信#Slave_SQL_Running:负责自己的slave mysql进程#如果执行了stop slave,SET GLOBAL sql_slave_skip_counter =1,start slave之后,show slave #status\G还是报错,则再次执行一遍stop slave,SET GLOBAL sql_slave_skip_counter =1,start #slave即可,最多执行3遍,即可消除所有错误。mysql> show slave status\G *************************** 1. row ***************************    Slave_IO_State: Waiting for master to send event     Master_Host: 192.168.110.188     Master_User: slave     Master_Port: 3306    Connect_Retry: 60    Master_Log_File: mysql-bin.000013   Read_Master_Log_Pos: 154    Relay_Log_File: node8-relay-bin.000037    Relay_Log_Pos: 320  Relay_Master_Log_File: mysql-bin.000013    Slave_IO_Running: Yes   Slave_SQL_Running: 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: 154    Relay_Log_Space: 693    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: 0Master_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: 1     Master_UUID: a8da7421-157f-11ea-b1bf-000c297c0226    Master_Info_File: /data/data/master.info     SQL_Delay: 0   SQL_Remaining_Delay: NULL  Slave_SQL_Running_State: Slave has read all relay log; waiting for more updates   Master_Retry_Count: 86400     Master_Bind:  Last_IO_Error_Timestamp:  Last_SQL_Error_Timestamp:    Master_SSL_Crl:   Master_SSL_Crlpath:   Retrieved_Gtid_Set:    Executed_Gtid_Set:     Auto_Position: 0   Replicate_Rewrite_DB:     Channel_Name:   Master_TLS_Version: 1 row in set (0.00 sec)#查看数据目录,可以发现Relay_Log_File[root@node8 ~]# ls /data/data/auto.cnf  ibdata1  ibtmp1  node8-relay-bin.000036 performance_schemahotdata   ib_logfile0 master.info node8-relay-bin.000037 relay-log.infoib_buffer_pool ib_logfile1 mysql  node8-relay-bin.index sys

6.3.3 配置从数据库服务器node9

​ node9的配置和node8一样,要注意的是配置文件my.cnf里server-id必须唯一,不能和node7,node8相同

6.3.4 在主服务器上查看状态

[root@node7 ~]# mysql -uroot -p123456#可以看到有两个slavemysql> show processlist\G*************************** 1. row ***************************  Id: 8 User: slave Host: 192.168.110.186:49414  db: NULLCommand: Binlog Dump Time: 4313 State: Master has sent all binlog to slave; waiting for more updates Info: NULL*************************** 2. row ***************************  Id: 10 User: slave Host: 192.168.110.187:33510  db: NULLCommand: Binlog Dump Time: 4208 State: Master has sent all binlog to slave; waiting for more updates Info: NULL*************************** 3. row ***************************  Id: 11 User: root Host: localhost  db: NULLCommand: Query Time: 0 State: starting Info: show processlist3 rows in set (0.00 sec)

6.3.5 插入数据测试主从同步

#在主服务器上插入数据mysql> use hotdata;Reading table information for completion of table and column namesYou can turn off this feature to get a quicker startup with -ADatabase changedmysql> insert into customers values (1,'张三','珠江新城','广州','广东省','1234567890@qq.com','china');Query OK, 1 row affected (0.10 sec)mysql> insert into customers values (2,'李四','天安门','北京','北京市','1234127890@qq.com','china');Query OK, 1 row affected (0.04 sec)mysql> insert into customers values (3,'王二麻子','钟鼓楼','昆明','云南省','1234567870@qq.com','china');Query OK, 1 row affected (0.01 sec)mysql> insert into customers values (4,'赵四','百花广场','佛山','广东省','1239867890@qq.com','china');Query OK, 1 row affected (0.00 sec)mysql> insert into customers values (5,'刘能','体育中心','广州','广东省','1234512890@qq.com','china');Query OK, 1 row affected (0.00 sec)mysql> insert into customers values (6,'谢广坤','体育西路','广州','广东省','1364567890@qq.com','china');Query OK, 1 row affected (0.00 sec)mysql> select * from customers; #查看数据+---------+--------------+--------------+-----------+------------+-------------------+--------------+| cust_id | cust_name | cust_address | cust_city | cust_state | cust_email  | cust_country |+---------+--------------+--------------+-----------+------------+-------------------+--------------+|  1 | 张三   | 珠江新城  | 广州  | 广东省  | 1234567890@qq.com | china  ||  2 | 李四   | 天安门  | 北京  | 北京市  | 1234127890@qq.com | china  ||  3 | 王二麻子  | 钟鼓楼  | 昆明  | 云南省  | 1234567870@qq.com | china  ||  4 | 赵四   | 百花广场  | 佛山  | 广东省  | 1239867890@qq.com | china  ||  5 | 刘能   | 体育中心  | 广州  | 广东省  | 1234512890@qq.com | china  ||  6 | 谢广坤  | 体育西路  | 广州  | 广东省  | 1364567890@qq.com | china  |+---------+--------------+--------------+-----------+------------+-------------------+--------------+6 rows in set (0.01 sec)mysql> exitBye#在两个slave上查看数据[root@node8 ~]# mysql -uroot -p123456#在node8上查看数据,发现数据已经同步mysql> select * from hotdata.customers;+---------+--------------+--------------+-----------+------------+-------------------+--------------+| cust_id | cust_name | cust_address | cust_city | cust_state | cust_email  | cust_country |+---------+--------------+--------------+-----------+------------+-------------------+--------------+|  1 | 张三   | 珠江新城  | 广州  | 广东省  | 1234567890@qq.com | china  ||  2 | 李四   | 天安门  | 北京  | 北京市  | 1234127890@qq.com | china  ||  3 | 王二麻子  | 钟鼓楼  | 昆明  | 云南省  | 1234567870@qq.com | china  ||  4 | 赵四   | 百花广场  | 佛山  | 广东省  | 1239867890@qq.com | china  ||  5 | 刘能   | 体育中心  | 广州  | 广东省  | 1234512890@qq.com | china  ||  6 | 谢广坤  | 体育西路  | 广州  | 广东省  | 1364567890@qq.com | china  |+---------+--------------+--------------+-----------+------------+-------------------+--------------+6 rows in set (0.00 sec)mysql> exitBye[root@node9 ~]# mysql -uroot -p123456#在node9上查看数据,发现数据已经同步mysql> select * from hotdata.customers;+---------+--------------+--------------+-----------+------------+-------------------+--------------+| cust_id | cust_name | cust_address | cust_city | cust_state | cust_email  | cust_country |+---------+--------------+--------------+-----------+------------+-------------------+--------------+|  1 | 张三   | 珠江新城  | 广州  | 广东省  | 1234567890@qq.com | china  ||  2 | 李四   | 天安门  | 北京  | 北京市  | 1234127890@qq.com | china  ||  3 | 王二麻子  | 钟鼓楼  | 昆明  | 云南省  | 1234567870@qq.com | china  ||  4 | 赵四   | 百花广场  | 佛山  | 广东省  | 1239867890@qq.com | china  ||  5 | 刘能   | 体育中心  | 广州  | 广东省  | 1234512890@qq.com | china  ||  6 | 谢广坤  | 体育西路  | 广州  | 广东省  | 1364567890@qq.com | china  |+---------+--------------+--------------+-----------+------------+-------------------+--------------+6 rows in set (0.00 sec)mysql> exitBye

注意

  • 主从同步,主数据库上添加数据,从数据库上同步,但是从数据库添加数据,主不同步
  • 由于是主从同步,如果主上删除了数据,那么从上的数据也就没了,因此建议在主上做定期备份(mysqldump)

自此,MySQL主从同步之一主多从架构已经搭建完毕。

6.3.6 彻底取消主从同步

​ 既然有搭建主从同步就有撤销主从同步,如果有撤销主从同步的需求,请看下文。

#在主库上执行#重置主记录信息mysql> reset master;Query OK, 0 rows affected (0.00 sec)mysql> show master status\G*************************** 1. row ***************************    File: mysql-bin.000001   Position: 154  Binlog_Do_DB: hotdata Binlog_Ignore_DB: mysqlExecuted_Gtid_Set: 1 row in set (0.00 sec)#在两个从库上执行mysql> stop slave;Query OK, 0 rows affected (0.00 sec)#清空从所有连接、信息记录mysql> reset slave all;Query OK, 0 rows affected (0.00 sec)mysql> show slave status\GEmpty set (0.00 sec)

​ 可见主库和从库都已经解除了主从关系,最后把配置文件中与主从相关的配置删除即可。

6.4 总结

​ MySQL主从同步之一主多从架构,一般用来做读写分离的,master负责写入数据,其他slave负责读取数据,这种架构最大问题I/O压力集中,在Master上多台同步影响IO

七.MySQL主从同步之主主双向同步架构

7.1 服务器规划

主机名IP操作系统版本MySQL版本角色
node7192.168.110.188CentOS 7.4.17085.7.26master,slave(既是主也是从)
node8192.168.110.186CentOS 7.4.17085.7.26master,slave(既是主也是从)

7.2 主从同步的原理

​ master将改变记录到二进制日志(binary log)中,slave将master的binary log events拷贝到它的中继日志(relay log),slave重做中继日志中的事件,修改salve上的数据。

7.3 部署MySQL主从同步之主主双向同步

7.3.1 配置数据库服务器node7

​ node7有双重身份,既是node8的主,也是node8的从。

7.3.1.1 创建需要同步的数据库及其表

[root@node7 ~]# mysql -uroot -p123456mysql> create database hotdata;  #创建热点数据库Query OK, 1 row affected (0.70 sec)mysql> use hotdata;Database changed#创建顾客表mysql> create table customers(cust_id int,cust_name varchar(30),cust_address varchar(50),cust_city varchar(30),cust_state varchar(50),cust_email varchar(30),cust_country varchar(50));Query OK, 0 rows affected (0.44 sec)mysql> desc customers; #查看表结构+--------------+-------------+------+-----+---------+-------+| Field  | Type  | Null | Key | Default | Extra |+--------------+-------------+------+-----+---------+-------+| cust_id  | int(11)  | YES |  | NULL |  || cust_name | varchar(30) | YES |  | NULL |  || cust_address | varchar(50) | YES |  | NULL |  || cust_city | varchar(30) | YES |  | NULL |  || cust_state | varchar(50) | YES |  | NULL |  || cust_email | varchar(30) | YES |  | NULL |  || cust_country | varchar(50) | YES |  | NULL |  |+--------------+-------------+------+-----+---------+-------+7 rows in set (0.36 sec)mysql> exitBye

7.3.1.2 修改MySQL配置文件

[root@node7 ~]# vim /etc/my.cnf#与主从同步相关的配置在#mysql replication下面[root@node7 ~]# cat /etc/my.cnf[client]port=3306socket=/data/run/mysql.sock[mysqld]port=3306socket=/data/run/mysql.sockpid_file=/data/run/mysql.piddatadir=/data/datadefault_storage_engine=InnoDBmax_allowed_packet=512Mmax_connections=2048open_files_limit=65535skip-name-resolvelower_case_table_names=1character-set-server=utf8mb4collation-server=utf8mb4_unicode_ciinit_connect='SET NAMES utf8mb4'innodb_buffer_pool_size=1024Minnodb_log_file_size=2048Minnodb_file_per_table=1innodb_flush_log_at_trx_commit=0key_buffer_size=64Mlog-error=/data/log/mysql_error.logslow_query_log=1slow_query_log_file=/data/log/mysql_slow_query.loglong_query_time=5tmp_table_size=32Mmax_heap_table_size=32Mquery_cache_type=0query_cache_size=0skip_ssl#mysql replication#logbin参数启用二进制日志,并把二进制日志放在/data/binlogs目录下log-bin=/data/binlogs/mysql-bin#数据库标志ID,唯一server-id=1#binlog-do-db可以被从服务器复制的库binlog-do-db=hotdata#binlog-ignore-db不可以被从服务器复制的库binlog-ignore-db=mysql

7.3.1.3 给node8授予replication的权限

#重启MySQL[root@node7 ~]# systemctl restart mysqld[root@node7 ~]# mysql -uroot -p123456#查看master状态mysql> show master status;+------------------+----------+--------------+------------------+-------------------+| File    | Position | Binlog_Do_DB | Binlog_Ignore_DB | Executed_Gtid_Set |+------------------+----------+--------------+------------------+-------------------+| mysql-bin.000001 |  154 | hotdata  | mysql   |     |+------------------+----------+--------------+------------------+-------------------+1 row in set (0.01 sec)mysql> grant replication slave on *.* to slave@'192.168.110.186' identified by '123456';Query OK, 0 rows affected, 1 warning (0.00 sec)#刷新权限mysql> flush privileges;Query OK, 0 rows affected (0.00 sec)mysql> exitBye

7.3.2 配置数据库服务器node8

​ node8有双重身份,既是node7的主,也是node7的从。

7.3.2.1 创建需要同步的数据库及其表

[root@node8 ~]# mysql -uroot -p123456mysql> create database hotdata;  #创建热点数据库Query OK, 1 row affected (0.70 sec)mysql> use hotdata;Database changed#创建顾客表mysql> create table customers(cust_id int,cust_name varchar(30),cust_address varchar(50),cust_city varchar(30),cust_state varchar(50),cust_email varchar(30),cust_country varchar(50));Query OK, 0 rows affected (0.44 sec)mysql> desc customers; #查看表结构+--------------+-------------+------+-----+---------+-------+| Field  | Type  | Null | Key | Default | Extra |+--------------+-------------+------+-----+---------+-------+| cust_id  | int(11)  | YES |  | NULL |  || cust_name | varchar(30) | YES |  | NULL |  || cust_address | varchar(50) | YES |  | NULL |  || cust_city | varchar(30) | YES |  | NULL |  || cust_state | varchar(50) | YES |  | NULL |  || cust_email | varchar(30) | YES |  | NULL |  || cust_country | varchar(50) | YES |  | NULL |  |+--------------+-------------+------+-----+---------+-------+7 rows in set (0.36 sec)mysql> exitBye

7.3.2.2 修改MySQL配置文件

[root@node8 ~]# vim /etc/my.cnf#主从同步相关的配置在#mysql replication配置下面[root@node8 ~]# cat /etc/my.cnf[client]port=3306socket=/data/run/mysql.sock[mysqld]port=3306socket=/data/run/mysql.sockpid_file=/data/run/mysql.piddatadir=/data/datadefault_storage_engine=InnoDBmax_allowed_packet=512Mmax_connections=2048open_files_limit=65535skip-name-resolvelower_case_table_names=1character-set-server=utf8mb4collation-server=utf8mb4_unicode_ciinit_connect='SET NAMES utf8mb4'innodb_buffer_pool_size=1024Minnodb_log_file_size=2048Minnodb_file_per_table=1innodb_flush_log_at_trx_commit=0key_buffer_size=64Mlog-error=/data/log/mysql_error.logslow_query_log=1slow_query_log_file=/data/log/mysql_slow_query.loglong_query_time=5tmp_table_size=32Mmax_heap_table_size=32Mquery_cache_type=0query_cache_size=0#mysql replication配置log-bin=/data/binlogs/mysql-binserver-id=2binlog-do-db=hotdatabinlog-ignore-db=mysql[root@node8 ~]# 重启MySQL[root@node8 ~]# systemctl restart mysqld

7.3.2.3 测试从账号slave能否登陆node7

[root@node8 ~]# mysql -uslave -p123456 -h 192.168.110.188#可以看到成功登陆node7mysql> show databases;+--------------------+| Database   |+--------------------+| information_schema |+--------------------+1 row in set (0.00 sec)mysql> exitBye

7.3.2.4 给node7赋予replication权限,并设置node8复制node7

[root@node8 ~]# mysql -uroot -p123456mysql> grant replication slave on *.* to slave@'192.168.110.188' identified by '123456';Query OK, 0 rows affected, 1 warning (0.01 sec)mysql> flush privileges;Query OK, 0 rows affected (0.01 sec)mysql> stop slave;Query OK, 0 rows affected, 1 warning (0.00 sec)mysql> change master to master_host='192.168.110.188',master_user='slave',master_password='123456';Query OK, 0 rows affected, 2 warnings (0.01 sec)mysql> start slave;Query OK, 0 rows affected (0.36 sec)#查看slave状态,如果Slave_IO_Running,Slave_SQL_Running都为yes,就表示okmysql> show slave status\G*************************** 1. row ***************************    Slave_IO_State: Waiting for master to send event     Master_Host: 192.168.110.188     Master_User: slave     Master_Port: 3306    Connect_Retry: 60    Master_Log_File: mysql-bin.000001   Read_Master_Log_Pos: 604    Relay_Log_File: node8-relay-bin.000002    Relay_Log_Pos: 817  Relay_Master_Log_File: mysql-bin.000001    Slave_IO_Running: Yes   Slave_SQL_Running: 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: 604    Relay_Log_Space: 1024    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: 0Master_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: 1     Master_UUID: a8da7421-157f-11ea-b1bf-000c297c0226    Master_Info_File: /data/data/master.info     SQL_Delay: 0   SQL_Remaining_Delay: NULL  Slave_SQL_Running_State: Slave has read all relay log; waiting for more updates   Master_Retry_Count: 86400     Master_Bind:  Last_IO_Error_Timestamp:  Last_SQL_Error_Timestamp:    Master_SSL_Crl:   Master_SSL_Crlpath:   Retrieved_Gtid_Set:    Executed_Gtid_Set:     Auto_Position: 0   Replicate_Rewrite_DB:     Channel_Name:   Master_TLS_Version: 1 row in set (0.00 sec)mysql> exitBye

7.3.3 配置数据库服务器node7

7.3.3.1 测试从账号slave能否登陆node8

[root@node7 ~]# mysql -uslave -p123456 -h 192.168.110.186#可以看到成功使用slave账号登录node8mysql> show databases;+--------------------+| Database   |+--------------------+| information_schema |+--------------------+1 row in set (0.00 sec)mysql> exitBye

7.3.3.2 设置node7复制node8

[root@node7 ~]# mysql -uroot -p123456mysql> change master to master_host='192.168.110.186',master_user='slave',master_password='123456';Query OK, 0 rows affected, 2 warnings (0.01 sec)mysql> start slave;Query OK, 0 rows affected (0.10 sec)#查看slave状态,如果Slave_IO_Running,Slave_SQL_Running都为yes,就表示okmysql> show slave status\G*************************** 1. row ***************************    Slave_IO_State: Waiting for master to send event     Master_Host: 192.168.110.186     Master_User: slave     Master_Port: 3306    Connect_Retry: 60    Master_Log_File: mysql-bin.000002   Read_Master_Log_Pos: 604    Relay_Log_File: node7-relay-bin.000003    Relay_Log_Pos: 817  Relay_Master_Log_File: mysql-bin.000002    Slave_IO_Running: Yes   Slave_SQL_Running: 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: 604    Relay_Log_Space: 1391    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: 0Master_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: 2     Master_UUID: f083c41e-1671-11ea-8342-000c29f7e789    Master_Info_File: /data/data/master.info     SQL_Delay: 0   SQL_Remaining_Delay: NULL  Slave_SQL_Running_State: Slave has read all relay log; waiting for more updates   Master_Retry_Count: 86400     Master_Bind:  Last_IO_Error_Timestamp:  Last_SQL_Error_Timestamp:    Master_SSL_Crl:   Master_SSL_Crlpath:   Retrieved_Gtid_Set:    Executed_Gtid_Set:     Auto_Position: 0   Replicate_Rewrite_DB:     Channel_Name:   Master_TLS_Version: 1 row in set (0.01 sec)mysql> show master status\G*************************** 1. row ***************************    File: mysql-bin.000001   Position: 604  Binlog_Do_DB: hotdata Binlog_Ignore_DB: mysqlExecuted_Gtid_Set: 1 row in set (0.00 sec)

7.3.4 插入数据测试主从是否同步

7.3.4.1 在node7上插入数据,查看node8 上有没有同步数据

#node7上插入数据mysql> insert into hotdata.customers values (1,'张三','珠江新城','广州','广东省','1234567890@qq.com','china');Query OK, 1 row affected (0.01 sec)mysql> insert into hotdata.customers values (2,'李四','天安门','北京','北京市','1234127890@qq.com','china');Query OK, 1 row affected (0.00 sec)mysql> insert into hotdata.customers values (3,'王二麻子','钟鼓楼','昆明','云南省','1234567870@qq.com','china');Query OK, 1 row affected (0.01 sec)mysql> insert into hotdata.customers values (4,'赵四','百花广场','佛山','广东省','1239867890@qq.com','china');Query OK, 1 row affected (0.01 sec)mysql> insert into hotdata.customers values (2,'李四','天安门','北京','北京市','1234127890@qq.com','china'); values (3,'王二麻子','钟鼓楼','昆明','云南省','1234567870@qq.com','china');insert into hotdata.customers values (4,'赵四','百花广场','佛山','广东省','1239867890@qq.com','china');Query OK, 1 row affected (0.00 sec)mysql> insert into hotdata.customers values (3,'王二麻子','钟鼓楼','昆明','云南省','1234567870@qq.com','china');Query OK, 1 row affected (0.00 sec)mysql> insert into hotdata.customers values (4,'赵四','百花广场','佛山','广东省','1239867890@qq.com','china');Query OK, 1 row affected (0.00 sec)mysql> select * from hotdata.customers;+---------+--------------+--------------+-----------+------------+-------------------+--------------+| cust_id | cust_name | cust_address | cust_city | cust_state | cust_email  | cust_country |+---------+--------------+--------------+-----------+------------+-------------------+--------------+|  1 | 张三   | 珠江新城  | 广州  | 广东省  | 1234567890@qq.com | china  ||  2 | 李四   | 天安门  | 北京  | 北京市  | 1234127890@qq.com | china  ||  3 | 王二麻子  | 钟鼓楼  | 昆明  | 云南省  | 1234567870@qq.com | china  ||  4 | 赵四   | 百花广场  | 佛山  | 广东省  | 1239867890@qq.com | china  ||  2 | 李四   | 天安门  | 北京  | 北京市  | 1234127890@qq.com | china  ||  3 | 王二麻子  | 钟鼓楼  | 昆明  | 云南省  | 1234567870@qq.com | china  ||  4 | 赵四   | 百花广场  | 佛山  | 广东省  | 1239867890@qq.com | china  |+---------+--------------+--------------+-----------+------------+-------------------+--------------+7 rows in set (0.00 sec)#在node8上查询数据mysql> select * from hotdata.customers;+---------+--------------+--------------+-----------+------------+-------------------+--------------+| cust_id | cust_name | cust_address | cust_city | cust_state | cust_email  | cust_country |+---------+--------------+--------------+-----------+------------+-------------------+--------------+|  1 | 张三   | 珠江新城  | 广州  | 广东省  | 1234567890@qq.com | china  ||  2 | 李四   | 天安门  | 北京  | 北京市  | 1234127890@qq.com | china  ||  3 | 王二麻子  | 钟鼓楼  | 昆明  | 云南省  | 1234567870@qq.com | china  ||  4 | 赵四   | 百花广场  | 佛山  | 广东省  | 1239867890@qq.com | china  ||  2 | 李四   | 天安门  | 北京  | 北京市  | 1234127890@qq.com | china  ||  3 | 王二麻子  | 钟鼓楼  | 昆明  | 云南省  | 1234567870@qq.com | china  ||  4 | 赵四   | 百花广场  | 佛山  | 广东省  | 1239867890@qq.com | china  |+---------+--------------+--------------+-----------+------------+-------------------+--------------+7 rows in set (0.00 sec)

7.3.4.2 在node8上插入数据,查看node7 上有没有同步数据

#node8上插入数据mysql> insert into hotdata.customers values (5,'刘能','体育中心','广州','广东省','1234512890@qq.com','china');tomers values (7,'人生的哲理','塔坡山','大理','云南省','2489567890@qq.com','china');insert into hotdata.customers values (8,'美剧','美剧','美国','美国','2489567890@qq.com','usa');Query OK, 1 row affected (0.01 sec)mysql> insert into hotdata.customers values (6,'谢广坤','体育西路','广州','广东省','1364567890@qq.com','china');Query OK, 1 row affected (0.00 sec)mysql> insert into hotdata.customers values (7,'人生的哲理','塔坡山','大理','云南省','2489567890@qq.com','china');Query OK, 1 row affected (0.00 sec)mysql> insert into hotdata.customers values (8,'美剧','美剧','美国','美国','2489567890@qq.com','usa');Query OK, 1 row affected (0.00 sec)mysql> select * from hotdata.customers;+---------+-----------------+--------------+-----------+------------+-------------------+--------------+| cust_id | cust_name  | cust_address | cust_city | cust_state | cust_email  | cust_country |+---------+-----------------+--------------+-----------+------------+-------------------+--------------+|  1 | 张三   | 珠江新城  | 广州  | 广东省  | 1234567890@qq.com | china  ||  2 | 李四   | 天安门  | 北京  | 北京市  | 1234127890@qq.com | china  ||  3 | 王二麻子  | 钟鼓楼  | 昆明  | 云南省  | 1234567870@qq.com | china  ||  4 | 赵四   | 百花广场  | 佛山  | 广东省  | 1239867890@qq.com | china  ||  2 | 李四   | 天安门  | 北京  | 北京市  | 1234127890@qq.com | china  ||  3 | 王二麻子  | 钟鼓楼  | 昆明  | 云南省  | 1234567870@qq.com | china  ||  4 | 赵四   | 百花广场  | 佛山  | 广东省  | 1239867890@qq.com | china  ||  5 | 刘能   | 体育中心  | 广州  | 广东省  | 1234512890@qq.com | china  ||  6 | 谢广坤   | 体育西路  | 广州  | 广东省  | 1364567890@qq.com | china  ||  7 | 人生的哲理  | 塔坡山  | 大理  | 云南省  | 2489567890@qq.com | china  ||  8 | 美剧   | 美剧   | 美国  | 美国  | 2489567890@qq.com | usa   |+---------+-----------------+--------------+-----------+------------+-------------------+--------------+11 rows in set (0.00 sec)#node7查询数据mysql> select * from hotdata.customers;+---------+-----------------+--------------+-----------+------------+-------------------+--------------+| cust_id | cust_name  | cust_address | cust_city | cust_state | cust_email  | cust_country |+---------+-----------------+--------------+-----------+------------+-------------------+--------------+|  1 | 张三   | 珠江新城  | 广州  | 广东省  | 1234567890@qq.com | china  ||  2 | 李四   | 天安门  | 北京  | 北京市  | 1234127890@qq.com | china  ||  3 | 王二麻子  | 钟鼓楼  | 昆明  | 云南省  | 1234567870@qq.com | china  ||  4 | 赵四   | 百花广场  | 佛山  | 广东省  | 1239867890@qq.com | china  ||  2 | 李四   | 天安门  | 北京  | 北京市  | 1234127890@qq.com | china  ||  3 | 王二麻子  | 钟鼓楼  | 昆明  | 云南省  | 1234567870@qq.com | china  ||  4 | 赵四   | 百花广场  | 佛山  | 广东省  | 1239867890@qq.com | china  ||  5 | 刘能   | 体育中心  | 广州  | 广东省  | 1234512890@qq.com | china  ||  6 | 谢广坤   | 体育西路  | 广州  | 广东省  | 1364567890@qq.com | china  ||  7 | 人生的哲理  | 塔坡山  | 大理  | 云南省  | 2489567890@qq.com | china  ||  8 | 美剧   | 美剧   | 美国  | 美国  | 2489567890@qq.com | usa   |+---------+-----------------+--------------+-----------+------------+-------------------+--------------+11 rows in set (0.01 sec)

由此可就主主双向同步搭建完毕。

7.3.5 彻底取消主从同步

既然有搭建主从同步就有撤销主从同步,如果有撤销主从同步的需求,请看下文。

由于是主主双向同步,所以两个mysql服务器都要清除matser和slave的配置。

#在两个MySQL上都执行如下操作,以node7为例#清除master配置mysql> reset master;Query OK, 0 rows affected (0.01 sec)mysql> show master status\G*************************** 1. row ***************************    File: mysql-bin.000001   Position: 154  Binlog_Do_DB: hotdata Binlog_Ignore_DB: mysqlExecuted_Gtid_Set: 1 row in set (0.00 sec)mysql> stop slave;Query OK, 0 rows affected (0.88 sec)mysql> reset slave all;Query OK, 0 rows affected (0.12 sec)#清除slave配置mysql> show slave status\GEmpty set (0.00 sec)

可见主库和从库都已经解除了主从关系,最后把配置文件中与主从相关的配置删除即可。

7.4 总结

​ 对于MySQL主从同步之主主双向同步架构,很多人误以为这样可以做到MySQL负载均衡,实际上非常不好,每个服务器需要做同样的同步更新,破坏了事物的隔离性和数据的一致性,不推荐。

八.MySQL主从同步之M-S-S架构

8.1 服务器规划

主机名IP操作系统版本MySQL版本角色
node7192.168.110.188CentOS 7.4.17085.7.26master(主)
node8192.168.110.186CentOS 7.4.17085.7.26slave中继(中继)
node9192.168.110.187CentOS 7.4.17085.7.26slave(从)

8.2 主从同步的原理

​ master将改变记录到二进制日志(binary log)中,slave将master的binary log events拷贝到它的中继日志(relay log),slave重做中继日志中的事件,修改salve上的数据。

​ 由于一主多从的结构IO压力集中在master上,所以使用一台slave作为中继,分担Master的压力,slave中继需要开启bin-log,并配置log-slave-updates,Slave中继可使用Black-hole存储引擎,不会把数据存储到磁盘,只记录二进制日志。

1575691837648

8.3 部署MySQL主从同步之M-S-S

8.3.1 配置主数据库服务器node7

8.3.1.1 创建需要同步的数据库及其表

[root@node7 ~]# mysql -uroot -p123456mysql> create database hotdata;  #创建热点数据库Query OK, 1 row affected (0.70 sec)mysql> use hotdata;Database changed#创建顾客表mysql> create table customers(cust_id int,cust_name varchar(30),cust_address varchar(50),cust_city varchar(30),cust_state varchar(50),cust_email varchar(30),cust_country varchar(50));Query OK, 0 rows affected (0.44 sec)mysql> desc customers; #查看表结构+--------------+-------------+------+-----+---------+-------+| Field  | Type  | Null | Key | Default | Extra |+--------------+-------------+------+-----+---------+-------+| cust_id  | int(11)  | YES |  | NULL |  || cust_name | varchar(30) | YES |  | NULL |  || cust_address | varchar(50) | YES |  | NULL |  || cust_city | varchar(30) | YES |  | NULL |  || cust_state | varchar(50) | YES |  | NULL |  || cust_email | varchar(30) | YES |  | NULL |  || cust_country | varchar(50) | YES |  | NULL |  |+--------------+-------------+------+-----+---------+-------+7 rows in set (0.36 sec)mysql> exitBye

8.3.1.2 授予node8 replication的权限

[root@node7 ~]# mysql -uroot -p123456mysql> grant replication slave on *.* to repl@'192.168.110.186' identified by '123456';Query OK, 0 rows affected, 1 warning (0.36 sec)mysql> flush privileges;Query OK, 0 rows affected (0.14 sec)mysql> exitBye

8.3.1.3 修改配置文件并重启

[root@node7 ~]# vim /etc/my.cnf#与主从同步相关的配置在#mysql replication下面[root@node7 ~]# cat /etc/my.cnf[client]port=3306socket=/data/run/mysql.sock[mysqld]port=3306socket=/data/run/mysql.sockpid_file=/data/run/mysql.piddatadir=/data/datadefault_storage_engine=InnoDBmax_allowed_packet=512Mmax_connections=2048open_files_limit=65535skip-name-resolvelower_case_table_names=1character-set-server=utf8mb4collation-server=utf8mb4_unicode_ciinit_connect='SET NAMES utf8mb4'innodb_buffer_pool_size=1024Minnodb_log_file_size=2048Minnodb_file_per_table=1innodb_flush_log_at_trx_commit=0key_buffer_size=64Mlog-error=/data/log/mysql_error.logslow_query_log=1slow_query_log_file=/data/log/mysql_slow_query.loglong_query_time=5tmp_table_size=32Mmax_heap_table_size=32Mquery_cache_type=0query_cache_size=0skip_ssl#mysql replicationlog-bin=/data/binlogs/mysql-bin#server-id=1必须唯一server-id=1binlog-do-db=hotdatabinlog-ignore-db=mysql#当每进行1次事务提交之后,MySQL将进行一次fsync之类的磁盘同步指令来将binlog_cache中的数据强制写入磁盘#sync-binlog具体解释请看:https://www.cnblogs.com/wt645631686/p/8109002.htmlsync-binlog=1#ROW模式(RBR):不记录每条sql语句的上下文信息,仅需记录哪条数据被修改了,修改成什么样了#具体解释查看:https://www.cnblogs.com/xingyunfashi/p/8431780.htmlbinlog-format=row[root@node7 ~]# systemctl restart mysqld

8.3.2 配置slave中继node8

8.3.2.1 创建需要同步的数据库及其表

[root@node8 ~]# mysql -uroot -p123456mysql> create database hotdata;  #创建热点数据库Query OK, 1 row affected (0.70 sec)mysql> use hotdata;Database changed#创建顾客表mysql> create table customers(cust_id int,cust_name varchar(30),cust_address varchar(50),cust_city varchar(30),cust_state varchar(50),cust_email varchar(30),cust_country varchar(50));Query OK, 0 rows affected (0.44 sec)mysql> desc customers; #查看表结构+--------------+-------------+------+-----+---------+-------+| Field  | Type  | Null | Key | Default | Extra |+--------------+-------------+------+-----+---------+-------+| cust_id  | int(11)  | YES |  | NULL |  || cust_name | varchar(30) | YES |  | NULL |  || cust_address | varchar(50) | YES |  | NULL |  || cust_city | varchar(30) | YES |  | NULL |  || cust_state | varchar(50) | YES |  | NULL |  || cust_email | varchar(30) | YES |  | NULL |  || cust_country | varchar(50) | YES |  | NULL |  |+--------------+-------------+------+-----+---------+-------+7 rows in set (0.36 sec)mysql> exitBye

8.3.2.2 修改配置文件并重启

##与主从同步相关的配置在#mysql replication下面[root@node8 ~]# cat /etc/my.cnf[client]port=3306socket=/data/run/mysql.sock[mysqld]port=3306socket=/data/run/mysql.sockpid_file=/data/run/mysql.piddatadir=/data/datadefault_storage_engine=InnoDBmax_allowed_packet=512Mmax_connections=2048open_files_limit=65535skip-name-resolvelower_case_table_names=1character-set-server=utf8mb4collation-server=utf8mb4_unicode_ciinit_connect='SET NAMES utf8mb4'innodb_buffer_pool_size=1024Minnodb_log_file_size=2048Minnodb_file_per_table=1innodb_flush_log_at_trx_commit=0key_buffer_size=64Mlog-error=/data/log/mysql_error.logslow_query_log=1slow_query_log_file=/data/log/mysql_slow_query.loglong_query_time=5tmp_table_size=32Mmax_heap_table_size=32Mquery_cache_type=0query_cache_size=0#mysql replication配置log-bin=/data/binlogs/mysql-binserver-id=2#log-slave-updates参数默认是关闭的状态,如果不手动设置,那么bin-log只会记录直接在该库上执行的SQL语##句,由replication机制的SQL线程读取relay-log而执行的SQL语句并不会记录到bin-log,那么就无法实现上#述的三级级联同步。log-slave-updates=1binlog-format=rowrelay-log=/data/data/relay-log.info[root@node8 ~]# [root@node8 ~]# systemctl restart mysqld

8.3.2.3 授权node8复制node7,并授予node9 replication的权限

[root@node8 ~]# mysql -uroot -p123456mysql> stop slave;Query OK, 0 rows affected, 1 warning (0.00 sec)mysql> change master to master_host='192.168.110.188',master_user='repl',master_password='123456';Query OK, 0 rows affected, 2 warnings (0.01 sec)mysql> start slave;Query OK, 0 rows affected (0.00 sec)mysql> show slave status \G*************************** 1. row ***************************    Slave_IO_State: Waiting for master to send event     Master_Host: 192.168.110.188     Master_User: repl     Master_Port: 3306    Connect_Retry: 60    Master_Log_File: mysql-bin.000002   Read_Master_Log_Pos: 154    Relay_Log_File: relay-log.000003    Relay_Log_Pos: 367  Relay_Master_Log_File: mysql-bin.000002    Slave_IO_Running: Yes   Slave_SQL_Running: 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: 154    Relay_Log_Space: 1230    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: 0Master_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: 1     Master_UUID: a8da7421-157f-11ea-b1bf-000c297c0226    Master_Info_File: /data/data/master.info     SQL_Delay: 0   SQL_Remaining_Delay: NULL  Slave_SQL_Running_State: Slave has read all relay log; waiting for more updates   Master_Retry_Count: 86400     Master_Bind:  Last_IO_Error_Timestamp:  Last_SQL_Error_Timestamp:    Master_SSL_Crl:   Master_SSL_Crlpath:   Retrieved_Gtid_Set:    Executed_Gtid_Set:     Auto_Position: 0   Replicate_Rewrite_DB:     Channel_Name:   Master_TLS_Version: 1 row in set (0.00 sec)mysql> grant replication slave on *.* to 'repl'@'192.168.110.187' identified by '123456';Query OK, 0 rows affected, 1 warning (0.00 sec)mysql> flush privileges;Query OK, 0 rows affected (0.00 sec)mysql> exitBye

8.3.3 配置从服务器node9

8.3.3.1 创建需要同步的数据库及其表

[root@node9 ~]# mysql -uroot -p123456mysql> create database hotdata;  #创建热点数据库Query OK, 1 row affected (0.70 sec)mysql> use hotdata;Database changed#创建顾客表mysql> create table customers(cust_id int,cust_name varchar(30),cust_address varchar(50),cust_city varchar(30),cust_state varchar(50),cust_email varchar(30),cust_country varchar(50));Query OK, 0 rows affected (0.44 sec)mysql> desc customers; #查看表结构+--------------+-------------+------+-----+---------+-------+| Field  | Type  | Null | Key | Default | Extra |+--------------+-------------+------+-----+---------+-------+| cust_id  | int(11)  | YES |  | NULL |  || cust_name | varchar(30) | YES |  | NULL |  || cust_address | varchar(50) | YES |  | NULL |  || cust_city | varchar(30) | YES |  | NULL |  || cust_state | varchar(50) | YES |  | NULL |  || cust_email | varchar(30) | YES |  | NULL |  || cust_country | varchar(50) | YES |  | NULL |  |+--------------+-------------+------+-----+---------+-------+7 rows in set (0.36 sec)mysql> exitBye

8.3.3.2 修改配置文件并重启

[root@node9 ~]# vim /etc/my.cnf[root@node9 ~]# cat /etc/my.cnf[client]port=3306socket=/data/run/mysql.sock[mysqld]port=3306socket=/data/run/mysql.sockpid_file=/data/run/mysql.piddatadir=/data/datadefault_storage_engine=InnoDBmax_allowed_packet=512Mmax_connections=2048open_files_limit=65535skip-name-resolvelower_case_table_names=1character-set-server=utf8mb4collation-server=utf8mb4_unicode_ciinit_connect='SET NAMES utf8mb4'innodb_buffer_pool_size=1024Minnodb_log_file_size=2048Minnodb_file_per_table=1innodb_flush_log_at_trx_commit=0key_buffer_size=64Mlog-error=/data/log/mysql_error.logslow_query_log=1slow_query_log_file=/data/log/mysql_slow_query.loglong_query_time=5tmp_table_size=32Mmax_heap_table_size=32Mquery_cache_type=0query_cache_size=0#mysql replication配置server-id=3log-bin=/data/binlogs/mysql-binbinlog-format=row#relay-log=/data/relaylog/relay.logrelay-log=/data/data/relay-log.info[root@node9 ~]# [root@node9 ~]# systemctl restart mysqld

8.3.3.3 指定node8为node9的主

[root@node9 ~]# mysql -uroot -p123456mysql> stop slave;Query OK, 0 rows affected, 1 warning (0.00 sec)mysql> change master to master_host='192.168.110.186',master_user='repl',master_password='123456';Query OK, 0 rows affected, 2 warnings (0.01 sec)mysql> flush privileges;Query OK, 0 rows affected (0.00 sec)mysql> start slave;Query OK, 0 rows affected (0.00 sec)mysql> show slave status \G*************************** 1. row ***************************    Slave_IO_State: Waiting for master to send event     Master_Host: 192.168.110.186     Master_User: repl     Master_Port: 3306    Connect_Retry: 60    Master_Log_File: mysql-bin.000002   Read_Master_Log_Pos: 1052    Relay_Log_File: relay-log.000003    Relay_Log_Pos: 1265  Relay_Master_Log_File: mysql-bin.000002    Slave_IO_Running: Yes   Slave_SQL_Running: 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: 1052    Relay_Log_Space: 1679    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: 0Master_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: 2     Master_UUID: f083c41e-1671-11ea-8342-000c29f7e789    Master_Info_File: /data/data/master.info     SQL_Delay: 0   SQL_Remaining_Delay: NULL  Slave_SQL_Running_State: Slave has read all relay log; waiting for more updates   Master_Retry_Count: 86400     Master_Bind:  Last_IO_Error_Timestamp:  Last_SQL_Error_Timestamp:    Master_SSL_Crl:   Master_SSL_Crlpath:   Retrieved_Gtid_Set:    Executed_Gtid_Set:     Auto_Position: 0   Replicate_Rewrite_DB:     Channel_Name:   Master_TLS_Version: 1 row in set (0.01 sec)mysql> exitBye

8.3.4 插入数据测试

#在node7上插入数据,查看node8和node9是否同步了数据#先在node7上插入数据[root@node7 ~]# mysql -uroot -p123456mysql> insert into hotdata.customers values (1,'张三','珠江新城','广州','广东省','1234567890@qq.com','china');mysql> insert into hotdata.customers values (2,'李四','天安门','北京','北京市','1234127890@qq.com','china');Query OK, 1 row affected (0.01 sec)mysql> insert into hotdata.customers values (3,'王二麻子','钟鼓楼','昆明','云南省','1234567870@qq.com','china');','云南省','2489567890@qq.com','china');Query OK, 1 row affected (0.09 sec)mysql> insert into hotdata.customers values (4,'赵四','百花广场','佛山','广东省','1239867890@qq.com','china');Query OK, 1 row affected (0.00 sec)mysql> insert into hotdata.customers values (5,'刘能','体育中心','广州','广东省','1234512890@qq.com','china');Query OK, 1 row affected (0.02 sec)mysql> insert into hotdata.customers values (6,'谢广坤','体育西路','广州','广东省','1364567890@qq.com','china');Query OK, 1 row affected (0.01 sec)mysql> insert into hotdata.customers values (7,'人生的哲理','塔坡山','大理','云南省','2489567890@qq.com','china');Query OK, 1 row affected (0.00 sec)mysql> mysql> mysql> select * from hotdata.customers;+---------+-----------------+--------------+-----------+------------+-------------------+--------------+| cust_id | cust_name  | cust_address | cust_city | cust_state | cust_email  | cust_country |+---------+-----------------+--------------+-----------+------------+-------------------+--------------+|  1 | 张三   | 珠江新城  | 广州  | 广东省  | 1234567890@qq.com | china  ||  2 | 李四   | 天安门  | 北京  | 北京市  | 1234127890@qq.com | china  ||  3 | 王二麻子  | 钟鼓楼  | 昆明  | 云南省  | 1234567870@qq.com | china  ||  4 | 赵四   | 百花广场  | 佛山  | 广东省  | 1239867890@qq.com | china  ||  5 | 刘能   | 体育中心  | 广州  | 广东省  | 1234512890@qq.com | china  ||  6 | 谢广坤   | 体育西路  | 广州  | 广东省  | 1364567890@qq.com | china  ||  7 | 人生的哲理  | 塔坡山  | 大理  | 云南省  | 2489567890@qq.com | china  |+---------+-----------------+--------------+-----------+------------+-------------------+--------------+7 rows in set (0.00 sec)#在node8上查看数据[root@node8 ~]# mysql -uroot -p123456mysql> select * from hotdata.customers;+---------+-----------------+--------------+-----------+------------+-------------------+--------------+| cust_id | cust_name  | cust_address | cust_city | cust_state | cust_email  | cust_country |+---------+-----------------+--------------+-----------+------------+-------------------+--------------+|  1 | 张三   | 珠江新城  | 广州  | 广东省  | 1234567890@qq.com | china  ||  2 | 李四   | 天安门  | 北京  | 北京市  | 1234127890@qq.com | china  ||  3 | 王二麻子  | 钟鼓楼  | 昆明  | 云南省  | 1234567870@qq.com | china  ||  4 | 赵四   | 百花广场  | 佛山  | 广东省  | 1239867890@qq.com | china  ||  5 | 刘能   | 体育中心  | 广州  | 广东省  | 1234512890@qq.com | china  ||  6 | 谢广坤   | 体育西路  | 广州  | 广东省  | 1364567890@qq.com | china  ||  7 | 人生的哲理  | 塔坡山  | 大理  | 云南省  | 2489567890@qq.com | china  |+---------+-----------------+--------------+-----------+------------+-------------------+--------------+7 rows in set (0.00 sec)#在node9上查看数据[root@node9 ~]# mysql -uroot -p123456mysql> select * from hotdata.customers;+---------+-----------------+--------------+-----------+------------+-------------------+--------------+| cust_id | cust_name  | cust_address | cust_city | cust_state | cust_email  | cust_country |+---------+-----------------+--------------+-----------+------------+-------------------+--------------+|  1 | 张三   | 珠江新城  | 广州  | 广东省  | 1234567890@qq.com | china  ||  2 | 李四   | 天安门  | 北京  | 北京市  | 1234127890@qq.com | china  ||  3 | 王二麻子  | 钟鼓楼  | 昆明  | 云南省  | 1234567870@qq.com | china  ||  4 | 赵四   | 百花广场  | 佛山  | 广东省  | 1239867890@qq.com | china  ||  5 | 刘能   | 体育中心  | 广州  | 广东省  | 1234512890@qq.com | china  ||  6 | 谢广坤   | 体育西路  | 广州  | 广东省  | 1364567890@qq.com | china  ||  7 | 人生的哲理  | 塔坡山  | 大理  | 云南省  | 2489567890@qq.com | china  |+---------+-----------------+--------------+-----------+------------+-------------------+--------------+7 rows in set (0.00 sec)

可以发现现在数据都已经同步了,但是有一个问题,slave中继node8也查到了数据,不符合需求。

设置node8需要同步的表hotdata.customers的存储引擎为blackhole

#关闭日志记录mysql> set sql_log_bin=off;Query OK, 0 rows affected (0.01 sec)#Blackhole引擎–"黑洞". 其作用正如其名字一样:任何写入到此引擎的数据均会被丢弃掉,不做实际存储;#Select语句的内容永远是空。 和Linux中的 /dev/null 文件完成的作用完全一致。mysql> alter table hotdata.customers ENGINE=blackhole;Query OK, 8 rows affected (0.01 sec)Records: 8 Duplicates: 0 Warnings: 0mysql> select * from hotdata.customers;Empty set (0.00 sec)

此时,node7上插入数据,node9同步数据,node8只分担node7的IO压力,不存储数据。

自此,MySQL主从同步之M-S-S架构搭建完毕。

8.4 总结

​ MySQL主从同步之M-S-S架构的好处是可以极大的减轻主节点的压力。

​ MySQL级联复制的另一用途是进行数据迁移。 比如新上的两台服务器B和C,要替换掉之前旧的服务器A,同时B和C是新的主从关系。因此,配置成级联复制,来迁移数据,也方便切换。

转换流程如下:

master A ------> slave B ------> slave C =转换为===> matser B ------> slave C

九.MySQL主从同步之多主多从架构

9.1 服务器规划

主机名IP操作系统版本MySQL版本角色
node6192.168.110.185CentOS 7.4.17085.7.26master,slave
node7192.168.110.188CentOS 7.4.17085.7.26master,slave
node8192.168.110.186CentOS 7.4.17085.7.26slave
node9192.168.110.187CentOS 7.4.17085.7.26slave

9.2 MySQL多主多从架构图

1575971034363

​ 架构图说明:node6和node8,node7和node9为一主一从架构,node6和node7为主主双向同步。

9.3 主从同步的原理

​ master将改变记录到二进制日志(binary log)中,slave将master的binary log events拷贝到它的中继日志(relay log),slave重做中继日志中的事件,修改salve上的数据。

​ 一主多从架构可以缓解读的压力,但是一旦主数据库宕机了,就不能写了,使用双主双从架构的话,一个主数据库宕机了,使用另一个主数据库替代即可。

9.4 部署MySQL主从同步之双主双从

9.4.1 配置主数据库服务器node6

9.4.1.1 创建需要同步的数据库及其表

[root@node6 ~]# mysql -uroot -p123456mysql> create database hotdata;  #创建热点数据库Query OK, 1 row affected (0.70 sec)mysql> use hotdata;Database changed#创建顾客表mysql> create table customers(cust_id int,cust_name varchar(30),cust_address varchar(50),cust_city varchar(30),cust_state varchar(50),cust_email varchar(30),cust_country varchar(50));Query OK, 0 rows affected (0.44 sec)mysql> desc customers; #查看表结构+--------------+-------------+------+-----+---------+-------+| Field  | Type  | Null | Key | Default | Extra |+--------------+-------------+------+-----+---------+-------+| cust_id  | int(11)  | YES |  | NULL |  || cust_name | varchar(30) | YES |  | NULL |  || cust_address | varchar(50) | YES |  | NULL |  || cust_city | varchar(30) | YES |  | NULL |  || cust_state | varchar(50) | YES |  | NULL |  || cust_email | varchar(30) | YES |  | NULL |  || cust_country | varchar(50) | YES |  | NULL |  |+--------------+-------------+------+-----+---------+-------+7 rows in set (0.36 sec)mysql> exitBye

9.4.1.2 修改node6的MySQL配置文件

[root@node6 ~]# vim /etc/my.cnf#MySQL主从同步的配置在#mysql replication下[root@node6 ~]# cat /etc/my.cnf[client]port=3306socket=/data/run/mysql.sockdefault-character-set=utf8[mysqld]port=3306socket=/data/run/mysql.sockpid_file=/data/run/mysql.piddatadir=/data/datadefault_storage_engine=InnoDBmax_allowed_packet=512Mmax_connections=2048open_files_limit=65535skip-name-resolvelower_case_table_names=1character-set-server=utf8mb4collation-server=utf8mb4_unicode_ciinit_connect='SET NAMES utf8mb4'innodb_buffer_pool_size=1024Minnodb_log_file_size=2048Minnodb_file_per_table=1innodb_flush_log_at_trx_commit=0key_buffer_size=64Mlog-error=/data/log/mysql_error.logslow_query_log=1slow_query_log_file=/data/log/mysql_slow_query.loglong_query_time=5tmp_table_size=32Mmax_heap_table_size=32Mquery_cache_type=0query_cache_size=0#mysql replication#server-id必须唯一server-id=4#logbin参数启用二进制日志,并把二进制日志放在/data/binlogs目录下log-bin=/data/binlogs/mysql-bin#binlog-do-db可以被从服务器复制的库binlog-do-db=hotdata#binlog-ignore-db不可以被从服务器复制的库binlog-ignore-db=mysql##auto_increment_increment,控制主键自增的自增步长,用于防止Master与Master之间复制出现重复自增字##段值,通常auto_increment_increment=n,有多少台主服务器,n 就设置为多少;auto_increment_increment=2#auto_increment_offset=1设置自增起始值,这里设置为1,这样Master的auto_increment字段产生的数值##是:1, 3, 5, 7, …等奇数ID,注意auto_increment_offset的设置,不同的master设置不应该一样,否则就##容易引起主键冲突,比如master1的offset=1,则master2的offset=2,master3的offset=3auto_increment_offset=1#在双主模式中,log-slave-updates 配置项一定要配置,否则在node6上进行了更新数据,在#node7和node8上会更新,但是在node9上不会更新log-slave-updates#sync_binlog表示每几次事务提交,MySQL把binlog缓存刷进日志文件中,默认是0,最安全的是设置为1;sync_binlog=1#重启MySQL[root@node6 ~]# systemctl restart mysqld[root@node6 ~]# systemctl status mysqld● mysqld.service - MySQL Server Loaded: loaded (/usr/lib/systemd/system/mysqld.service; enabled; vendor preset: disabled) Active: active (running) since Thu 2019-12-12 15:02:26 CST; 28s ago  Docs: man:mysqld(5.7)   Process: 3753 ExecStart=/usr/local/mysql/bin/mysqld --daemonize --pid-file=/data/run/mysql.pid $MYSQLD_OPTS (code=exited, status=0/SUCCESS) Main PID: 3755 (mysqld) CGroup: /system.slice/mysqld.service   └─3755 /usr/local/mysql/bin/mysqld --daemonize --pid-file=/data/run/mysql.pidDec 12 15:02:25 node6 systemd[1]: Starting MySQL Server...Dec 12 15:02:26 node6 systemd[1]: Started MySQL Server.

9.4.1.3 node6创建复制账号并授权给node7和node8

[root@node6 ~]# mysql -uroot -p123456mysql> grant replication slave on *.* to 'copy'@'192.168.110.188' identified by '123456';Query OK, 0 rows affected, 1 warning (0.01 sec)mysql> grant replication slave on *.* to 'copy'@'192.168.110.186' identified by '123456';Query OK, 0 rows affected, 1 warning (0.00 sec)mysql> flush privileges;Query OK, 0 rows affected (0.00 sec)

9.4.2 配置主数据库服务器node7

9.4.2.1 创建需要同步的数据库及其表

[root@node7 ~]# mysql -uroot -p123456mysql> create database hotdata;  #创建热点数据库Query OK, 1 row affected (0.70 sec)mysql> use hotdata;Database changed#创建顾客表mysql> create table customers(cust_id int,cust_name varchar(30),cust_address varchar(50),cust_city varchar(30),cust_state varchar(50),cust_email varchar(30),cust_country varchar(50));Query OK, 0 rows affected (0.44 sec)mysql> desc customers; #查看表结构+--------------+-------------+------+-----+---------+-------+| Field  | Type  | Null | Key | Default | Extra |+--------------+-------------+------+-----+---------+-------+| cust_id  | int(11)  | YES |  | NULL |  || cust_name | varchar(30) | YES |  | NULL |  || cust_address | varchar(50) | YES |  | NULL |  || cust_city | varchar(30) | YES |  | NULL |  || cust_state | varchar(50) | YES |  | NULL |  || cust_email | varchar(30) | YES |  | NULL |  || cust_country | varchar(50) | YES |  | NULL |  |+--------------+-------------+------+-----+---------+-------+7 rows in set (0.36 sec)mysql> exitBye

9.4.2.2 修改node7的MySQL配置文件

[root@node7 ~]# vim /etc/my.cnf[root@node7 ~]# cat /etc/my.cnf[client]port=3306socket=/data/run/mysql.sockdefault-character-set=utf8[mysqld]port=3306socket=/data/run/mysql.sockpid_file=/data/run/mysql.piddatadir=/data/datadefault_storage_engine=InnoDBmax_allowed_packet=512Mmax_connections=2048open_files_limit=65535skip-name-resolvelower_case_table_names=1character-set-server=utf8mb4collation-server=utf8mb4_unicode_ciinit_connect='SET NAMES utf8mb4'innodb_buffer_pool_size=1024Minnodb_log_file_size=2048Minnodb_file_per_table=1innodb_flush_log_at_trx_commit=0key_buffer_size=64Mlog-error=/data/log/mysql_error.logslow_query_log=1slow_query_log_file=/data/log/mysql_slow_query.loglong_query_time=5tmp_table_size=32Mmax_heap_table_size=32Mquery_cache_type=0query_cache_size=0skip_ssl#mysql replicationlog-bin=/data/binlogs/mysql-binserver-id=1binlog-do-db=hotdatabinlog-ignore-db=mysqlauto_increment_increment=2auto_increment_offset=2log-slave-updatessync_binlog=1[root@node7 ~]# systemctl restart mysqld[root@node7 ~]# systemctl status mysqld● mysqld.service - MySQL Server Loaded: loaded (/usr/lib/systemd/system/mysqld.service; enabled; vendor preset: disabled) Active: active (running) since Thu 2019-12-12 15:02:29 CST; 26s ago  Docs: man:mysqld(5.7)   Process: 14635 ExecStart=/usr/local/mysql/bin/mysqld --daemonize --pid-file=/data/run/mysql.pid $MYSQLD_OPTS (code=exited, status=0/SUCCESS) Main PID: 14637 (mysqld) CGroup: /system.slice/mysqld.service   └─14637 /usr/local/mysql/bin/mysqld --daemonize --pid-file=/data/run/mysql.pidDec 12 15:02:25 node7 systemd[1]: Starting MySQL Server...Dec 12 15:02:29 node7 systemd[1]: Started MySQL Server.

9.4.2.3 node7创建复制账号并授权给node6和node9

[root@node7 ~]# mysql -uroot -p123456mysql> grant replication slave on *.* to 'copy'@'192.168.110.185' identified by '123456';Query OK, 0 rows affected, 1 warning (0.12 sec)mysql> grant replication slave on *.* to 'copy'@'192.168.110.187' identified by '123456';Query OK, 0 rows affected, 1 warning (0.00 sec)mysql> flush privileges;Query OK, 0 rows affected (0.01 sec)

9.4.3 配置从数据库服务器node8

9.4.3.1 创建需要同步的数据库及其表

[root@node8 ~]# mysql -uroot -p123456mysql> create database hotdata;  #创建热点数据库Query OK, 1 row affected (0.70 sec)mysql> use hotdata;Database changed#创建顾客表mysql> create table customers(cust_id int,cust_name varchar(30),cust_address varchar(50),cust_city varchar(30),cust_state varchar(50),cust_email varchar(30),cust_country varchar(50));Query OK, 0 rows affected (0.44 sec)mysql> desc customers; #查看表结构+--------------+-------------+------+-----+---------+-------+| Field  | Type  | Null | Key | Default | Extra |+--------------+-------------+------+-----+---------+-------+| cust_id  | int(11)  | YES |  | NULL |  || cust_name | varchar(30) | YES |  | NULL |  || cust_address | varchar(50) | YES |  | NULL |  || cust_city | varchar(30) | YES |  | NULL |  || cust_state | varchar(50) | YES |  | NULL |  || cust_email | varchar(30) | YES |  | NULL |  || cust_country | varchar(50) | YES |  | NULL |  |+--------------+-------------+------+-----+---------+-------+7 rows in set (0.36 sec)mysql> exitBye

9.4.3.2 修改node8的MySQL配置文件

[root@node8 ~]# vim /etc/my.cnf[root@node8 ~]# cat /etc/my.cnf[client]port=3306socket=/data/run/mysql.sockdefault-character-set=utf8[mysqld]port=3306socket=/data/run/mysql.sockpid_file=/data/run/mysql.piddatadir=/data/datadefault_storage_engine=InnoDBmax_allowed_packet=512Mmax_connections=2048open_files_limit=65535skip-name-resolvelower_case_table_names=1character-set-server=utf8mb4collation-server=utf8mb4_unicode_ciinit_connect='SET NAMES utf8mb4'innodb_buffer_pool_size=1024Minnodb_log_file_size=2048Minnodb_file_per_table=1innodb_flush_log_at_trx_commit=0key_buffer_size=64Mlog-error=/data/log/mysql_error.logslow_query_log=1slow_query_log_file=/data/log/mysql_slow_query.loglong_query_time=5tmp_table_size=32Mmax_heap_table_size=32Mquery_cache_type=0query_cache_size=0#mysql replication配置server-id=2[root@node8 ~]# systemctl restart mysqld[root@node8 ~]# systemctl status mysqld● mysqld.service - MySQL Server Loaded: loaded (/usr/lib/systemd/system/mysqld.service; enabled; vendor preset: disabled) Active: active (running) since Thu 2019-12-12 15:02:28 CST; 27s ago  Docs: man:mysqld(5.7)   Process: 24078 ExecStart=/usr/local/mysql/bin/mysqld --daemonize --pid-file=/data/run/mysql.pid $MYSQLD_OPTS (code=exited, status=0/SUCCESS) Main PID: 24080 (mysqld) CGroup: /system.slice/mysqld.service   └─24080 /usr/local/mysql/bin/mysqld --daemonize --pid-file=/data/run/mysql.pidDec 12 15:02:25 node8 systemd[1]: Starting MySQL Server...Dec 12 15:02:28 node8 systemd[1]: Started MySQL Server.

9.4.4 配置从数据库服务器node9

9.4.4.1 创建需要同步的数据库及其表

[root@node9 ~]# mysql -uroot -p123456mysql> create database hotdata;  #创建热点数据库Query OK, 1 row affected (0.70 sec)mysql> use hotdata;Database changed#创建顾客表mysql> create table customers(cust_id int,cust_name varchar(30),cust_address varchar(50),cust_city varchar(30),cust_state varchar(50),cust_email varchar(30),cust_country varchar(50));Query OK, 0 rows affected (0.44 sec)mysql> desc customers; #查看表结构+--------------+-------------+------+-----+---------+-------+| Field  | Type  | Null | Key | Default | Extra |+--------------+-------------+------+-----+---------+-------+| cust_id  | int(11)  | YES |  | NULL |  || cust_name | varchar(30) | YES |  | NULL |  || cust_address | varchar(50) | YES |  | NULL |  || cust_city | varchar(30) | YES |  | NULL |  || cust_state | varchar(50) | YES |  | NULL |  || cust_email | varchar(30) | YES |  | NULL |  || cust_country | varchar(50) | YES |  | NULL |  |+--------------+-------------+------+-----+---------+-------+7 rows in set (0.36 sec)mysql> exitBye

9.4.4.2 修改node9的MySQL配置文件

[root@node9 ~]# vim /etc/my.cnf[root@node9 ~]# cat /etc/my.cnf[client]port=3306socket=/data/run/mysql.sockdefault-character-set=utf8[mysqld]port=3306socket=/data/run/mysql.sockpid_file=/data/run/mysql.piddatadir=/data/datadefault_storage_engine=InnoDBmax_allowed_packet=512Mmax_connections=2048open_files_limit=65535skip-name-resolvelower_case_table_names=1character-set-server=utf8mb4collation-server=utf8mb4_unicode_ciinit_connect='SET NAMES utf8mb4'innodb_buffer_pool_size=1024Minnodb_log_file_size=2048Minnodb_file_per_table=1innodb_flush_log_at_trx_commit=0key_buffer_size=64Mlog-error=/data/log/mysql_error.logslow_query_log=1slow_query_log_file=/data/log/mysql_slow_query.loglong_query_time=5tmp_table_size=32Mmax_heap_table_size=32Mquery_cache_type=0query_cache_size=0#mysql replication配置server-id=3[root@node9 ~]# systemctl restart mysqld[root@node9 ~]# systemctl status mysqld● mysqld.service - MySQL Server Loaded: loaded (/usr/lib/systemd/system/mysqld.service; enabled; vendor preset: disabled) Active: active (running) since Thu 2019-12-12 15:02:27 CST; 28s ago  Docs: man:mysqld(5.7)   Process: 27714 ExecStart=/usr/local/mysql/bin/mysqld --daemonize --pid-file=/data/run/mysql.pid $MYSQLD_OPTS (code=exited, status=0/SUCCESS) Main PID: 27716 (mysqld) CGroup: /system.slice/mysqld.service   └─27716 /usr/local/mysql/bin/mysqld --daemonize --pid-file=/data/run/mysql.pidDec 12 15:02:25 node9 systemd[1]: Starting MySQL Server...Dec 12 15:02:27 node9 systemd[1]: Started MySQL Server.

9.4.5 在slave上配置master(所有节点)

​ 四台MySQL都扮演slave的角色,所以所有节点都要配置

#在所有节点的MySQL上执行如下mysql> stop slave;Query OK, 0 rows affected, 1 warning (0.00 sec)mysql> reset slave;Query OK, 0 rows affected (0.00 sec)mysql> reset master;Query OK, 0 rows affected (0.03 sec)#因为node6和node9是node7的从,node7和node8是node6的从#所以在node6和node9上执行mysql> change master to master_host='192.168.110.188',master_user='copy',master_password='123456';Query OK, 0 rows affected, 2 warnings (0.02 sec)#在node7和node8上执行mysql> change master to master_host='192.168.110.185',master_user='copy',master_password='123456';Query OK, 0 rows affected, 2 warnings (0.04 sec)

9.4.6 启动slave,让四台MySQL进入主从复制状态

#在所有MySQL节点上执行#mysql> start slave;#mysql> show master status\G#mysql> show slave status\G#如果执行show slave status\G之后,Slave_IO_Running和Slave_SQL_Running均为yes,则说明主从同步成功#下面以node6为例,其他节点类似mysql> start slave;Query OK, 0 rows affected (0.05 sec)mysql> show master status\G*************************** 1. row ***************************    File: mysql-bin.000001   Position: 154  Binlog_Do_DB: hotdata Binlog_Ignore_DB: mysqlExecuted_Gtid_Set: 1 row in set (0.00 sec)mysql> show slave status\G*************************** 1. row ***************************    Slave_IO_State: Waiting for master to send event     Master_Host: 192.168.110.188     Master_User: copy     Master_Port: 3306    Connect_Retry: 60    Master_Log_File: mysql-bin.000001   Read_Master_Log_Pos: 154    Relay_Log_File: node6-relay-bin.000002    Relay_Log_Pos: 367  Relay_Master_Log_File: mysql-bin.000001    Slave_IO_Running: Yes   Slave_SQL_Running: 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: 154    Relay_Log_Space: 574    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: 0Master_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: 1     Master_UUID: a8da7421-157f-11ea-b1bf-000c297c0226    Master_Info_File: /data/data/master.info     SQL_Delay: 0   SQL_Remaining_Delay: NULL  Slave_SQL_Running_State: Slave has read all relay log; waiting for more updates   Master_Retry_Count: 86400     Master_Bind:  Last_IO_Error_Timestamp:  Last_SQL_Error_Timestamp:    Master_SSL_Crl:   Master_SSL_Crlpath:   Retrieved_Gtid_Set:    Executed_Gtid_Set:     Auto_Position: 0   Replicate_Rewrite_DB:     Channel_Name:   Master_TLS_Version: 1 row in set (0.00 sec)mysql> exitBye

9.4.7 测试验证双主双从

#测试一:在node6上插入一条数据,其他所有mysql都应该同步这条数据#测试二:在node7上插入一条数据,其他所有mysql都应该同步这条数据#测试三:停止node6上的MySQL(模拟故障),在node7上插入一条数据,只有node9上同步该数据,重启node6之后(模拟故障恢复),node6和node8也应该同步该数据。#如果上述测试都通过,则说明MySQL双主双从架构搭建完毕并功能无误。

9.5 总结

​ MySQL主从同步之多主多从架构可以实现MySQL服务的高可用,即使一个MySQL主数据库宕机,使用另外一个主数据库替代即可,避免了数据的不同步和服务的不可用。

十.参考资料

https://www.cnblogs.com/wuchangsoft/p/10374438.html


没有评论:

发表评论