第二十七课预习任务

1.MySQL主从介绍

1.2 MySQL主从原理

2.准备工作

3.配置主

3.1 修改配置文件

3.2 备份相关数据库文件

3.3 创建同步数据用户

4. 配置从

4.1 修改配置文件

4.2 将主上的数据库导入从中

4.3 启动主从同步

5.测试主从同步

5.1 在主机器上创建一个库

5.2 在从机器上查询库

5.3 主从同步中常见的问题


1.MySQL主从介绍

1.1 Mysql的Replication(复制)是一个异步的复制过程,从一个 Mysql instance(我们称之为 Master)复制到另一个Mysql instance(我们称之 Slave)。在 Master 与 Slave之间的实现整个复制过程主要由三个线程来完成,其中两个线程(Sql线程和IO线程)在 Slave 端,另外一个线程(IO线程)在Master端。

1.2 MySQL主从原理

主库上的二进制bin-log中记录主库的所有DML操作,同时在主库上运行有一个IO线程,用于响应从库上的bin-log日志读取请求;在从库上运行有一个IO线程和一个SQL线程,IO线程会实时通过网络请求去从库上读取bin-log日志,然后写入到自身的relay-log日志文件中,同时运行在从库上的SQL线程会去解析并读取relay-log,然后在自身库上执行读取到的SQL,完成主从数据的同步,示意图如下:

a、主库上会开启了二进制bin-log日志记录,同时运行有一个IO线程;
b、主库上对于需要同步的数据库或者表所发生的所有DML操作都会被记录到bin-log二进制日志文件中;
c、从库上开启relay-log日志,同时运行有一个IO线程和一个SQL线程;
d、IO线程负责从主库中读取bin-log二进制日志,并写入到本地的relay-log日志中,同时记录从库所读取到的主库的日志文件位置信息,以便下次从这个位置点再次读取;
e、SQL线程负责从本地的relay-log日志中读取同步到的二进制日志,并解析为数据库可以识别的SQL语句,然后应用到本地数据库,完成同步;
f、执行完relay-log中的操作之后,进入睡眠状态,等待主库产生新的更新;

2.准备工作

1.首先我们需要准备两台虚拟机并装上mysql这个安装方法就不多介绍了。

这是第一台虚拟机我们会把这台做为主,也就是服务器IP地址:192.168.139.168

ens33: <BROADCAST,MULTICAST,UP,LOWER_UP> mtu 1500 qdisc pfifo_fast state UP group default qlen 1000
    link/ether 00:0c:29:ec:fc:cf brd ff:ff:ff:ff:ff:ff
    inet 192.168.139.168/24 brd 192.168.139.255 scope global noprefixroute ens33
       valid_lft forever preferred_lft forever
    inet6 fe80::20c:29ff:feec:fccf/64 scope link tentative dadfailed 
       valid_lft forever preferred_lft forever
[root@knightlai ~]# ps aux |grep mysql
root        919  0.0  0.1 115432  1704 ?        S    Oct10   0:00 /bin/sh /usr/local/mysql/bin/mysqld_safe --datadir=/data/mysql --pid-file=/data/mysql/mysql.pid
mysql      1099  0.0 45.9 1302800 459000 ?      Sl   Oct10   1:08 /usr/local/mysql/bin/mysqld --basedir=/usr/local/mysql --datadir=/data/mysql --plugin-dir=/usr/local/mysql/lib/plugin --user=mysql --log-error=/data/mysql/error.log --pid-file=/data/mysql/mysql.pid --socket=/tmpmysql.sock
root       4461  0.0  0.0 112704   956 pts/1    R+   01:34   0:00 grep --color=auto mysql

这是第二台虚拟机也就是从。这个IP地址:192.168.139.112

ens36: <BROADCAST,MULTICAST,UP,LOWER_UP> mtu 1500 qdisc pfifo_fast state UP group default qlen 1000
    link/ether 00:0c:29:b1:e4:36 brd ff:ff:ff:ff:ff:ff
    inet 192.168.139.112/24 brd 192.168.139.255 scope global noprefixroute dynamic ens36
       valid_lft 3119sec preferred_lft 3119sec
[root@knightlai ~]# ps aux |grep mysql
root        870  0.0  0.1 115432  1684 ?        S    Sep14   0:00 /bin/sh /usr/local/mysql/bin/mysqld_safe --datadir=/data/mysql --pid-file=/data/mysql/knightlai.pid
mysql      1033  0.0 45.3 1302728 452976 ?      Sl   Sep14   2:09 /usr/local/mysql/bin/mysqld --basedir=/usr/local/mysql --datadir=/data/mysql --plugin-dir=/usr/local/mysql/lib/plugin --user=mysql --log-error=knightlai.err --pid-file=/data/mysql/knightlai.pid
root      14268  0.0  0.0 112704   960 pts/0    R+   06:19   0:00 grep --color=auto mysql

两台虚拟机上安装都是mysql 5.6

主
[root@knightlai ~]# mysql --version
/usr/local/mysql/bin/mysql  Ver 14.14 Distrib 5.6.39, for linux-glibc2.12 (x86_64) using  EditLine wrapp


从
[root@knightlai ~]# mysql --version
/usr/local/mysql/bin/mysql  Ver 14.14 Distrib 5.6.39, for linux-glibc2.12 (x86_64) using  EditLine wrapp

3.配置主

3.1 修改配置文件

[root@knightlai ~]# vim /etc/my.cnf
server_id=168
log_bin=master
[root@knightlai ~]# /etc/init.d/mysqld restart
Shutting down MySQL.. SUCCESS! 
Starting MySQL. SUCCESS! 

(1)server-id:用来标识一个唯一的实例,如果是在同一个局域网内,可以使用ip地址的最后一段,要保证唯一
(2)log_bin:二进制日志文件的路径,mysql用户对该路径必须具有读写权限

3.2 备份相关数据库文件

//备份一个zrlog库
[root@knightlai ~]# mysqldump -uroot -p123456 zrlog > /tmp/zrlog.sql
Warning: Using a password on the command line interface can be insecure.

//新建一个test2018库用来测试
[root@knightlai ~]# mysql -uroot -p123456 -e "create database test2018"
Warning: Using a password on the command line interface can be insecure.
//将zrlog库的数据恢复到test2018中
[root@knightlai ~]# mysql -uroot -p123456 test2018 </tmp/zrlog.sql 
Warning: Using a password on the command line interface can be insecure.
+--------------------+
| Database           |
+--------------------+
| information_schema |
| db1                |
| mysql              |
| performance_schema |
| test               |
| test2018           |
| zrlog              |
+--------------------+

3.3 创建同步数据用户

[root@knightlai ~]# mysql -uroot -p123456
mysql> GRANT REPLICATION SLAVE,REPLICATION CLIENT ON *.* to 'repl'@'127.0.0.1' IDENTIFIED BY 'repl';
Query OK, 0 rows affected (0.00 sec)

//刷新表并锁表,为了保证数据的一致性
mysql> flush tables with read lock;
Query OK, 0 rows affected (0.00 sec)


查看主库的二进制日志文件及位置点
mysql> show master status; 
+---------------+----------+--------------+------------------+-------------------+
| File          | Position | Binlog_Do_DB | Binlog_Ignore_DB | Executed_Gtid_Set |
+---------------+----------+--------------+------------------+-------------------+
| master.000007 |      120 |              |                  |                   |
+---------------+----------+--------------+------------------+-------------------+
1 row in set (0.00 sec)


4. 配置从

4.1 修改配置文件

//配置server-id需要和主上不一样
[root@knightlai ~]# vim /etc/my.cnf
server-id=169

[root@knightlai ~]# /etc/init.d/mysqld restart
Shutting down MySQL.... SUCCESS! 
Starting MySQL........... SUCCESS! 

4.2 将主上的数据库导入从中

//将主上的数据库文件同步从上
[root@knightlai ~]# scp 192.168.139.168:/tmp/*.sql /tmp/
The authenticity of host '192.168.139.168 (192.168.139.168)' can't be established.
ECDSA key fingerprint is SHA256:JEmKUtRSqXMbbymFgNEWnDQEgCUTjzFYFays6NrK58c.
ECDSA key fingerprint is MD5:2c:c4:cf:bc:1a:b8:f5:e2:03:2c:22:c3:0f:53:5c:be.
Are you sure you want to continue connecting (yes/no)? yes
Warning: Permanently added '192.168.139.168' (ECDSA) to the list of known hosts.
[email protected]'s password: 
test2018.sql                                                                                             100%   16KB 777.8KB/s   00:00    
zrlog.sql                                                                                                100%   16KB   2.9MB/s   00:00

//登录数据库创建数据库并恢复数据
[root@knightlai ~]# mysql -uroot
mysql> create database zrlog;
Query OK, 1 row affected (0.00 sec)

mysql> create database test2018;
Query OK, 1 row affected (0.00 sec)

//将数据恢复到数据库中
[root@knightlai ~]# mysqldump -uroot zrlog</tmp/zrlog.sql 
-- MySQL dump 10.13  Distrib 5.6.39, for linux-glibc2.12 (x86_64)
--
-- Host: localhost    Database: zrlog
-- ------------------------------------------------------
-- Server version	5.6.39

/*!40101 SET @OLD_CHARACTER_SET_CLIENT=@@CHARACTER_SET_CLIENT */;
/*!40101 SET @OLD_CHARACTER_SET_RESULTS=@@CHARACTER_SET_RESULTS */;


[root@knightlai ~]# mysqldump -uroot test2018</tmp/test2018.sql 
-- MySQL dump 10.13  Distrib 5.6.39, for linux-glibc2.12 (x86_64)
--
-- Host: localhost    Database: test2018
-- ------------------------------------------------------
-- Server version	5.6.39

/*!40101 SET @OLD_CHARACTER_SET_CLIENT=@@CHARACTER_SET_CLIENT */;
/*!40101 SET @OLD_CHARACTER_SET_RESULTS=@@CHARACTER_SET_RESULTS */;
/*!40101 SET @OLD_COLLATION_CONNECTION=@@COLLATION_CONNECTION */;
/*!40101 SET NAMES utf8 */;

4.3 启动主从同步

修改从库上的master指向,使其指向主库,并且从主库上最新的二进制日志和位置点开始同步,然后启动主从同步

mysql> CHANGE MASTER TO master_host = '127.0.0.1',master_port = 3306,master_user='repl',master_password='repl',master_log_file='master.000007',master_log_pos = 120; 
Query OK, 0 rows affected, 2 warnings (0.07 sec)

master_host:主库的主机名或者IP地址
master_port:主库的端口号,必须为整数,不能加引号,否则会提示错误
master_user:在主库上添加的复制用户名称
master_password:在主库上添加的复制用户密码
master_log_file:主库当前的二进制日志文件名称
master_log_pos:主库当前的二进制文件位置点,整数,不可加引号,否则会提示错误


mysql> start slave;
Query OK, 0 rows affected (0.03 sec)

mysql> show slave status\G
*************************** 1. row ***************************
               Slave_IO_State: Connecting to master
                  Master_Host: 127.0.0.1
                  Master_User: repl
                  Master_Port: 3306
                Connect_Retry: 60
              Master_Log_File: master.000007
          Read_Master_Log_Pos: 120
               Relay_Log_File: knightlai-relay-bin.000001
                Relay_Log_Pos: 4
        Relay_Master_Log_File: master.000007
             Slave_IO_Running: Yes
            Slave_SQL_Running: Yes


上述结果中Slave_IO_Running和Slave_SQL_Running都为Yes表示主从同步成功

5.测试主从同步

5.1 在主机器上创建一个库

mysql> create database test1012;
Query OK, 1 row affected (0.04 sec)

mysql> show databases;
+--------------------+
| Database           |
+--------------------+
| information_schema |
| db1                |
| mysql              |
| performance_schema |
| test               |
| test1012           |
| test2018           |
| zrlog              |
+--------------------+
8 rows in set (0.06 sec)

//删除一个库文件
mysql> drop test2018;
ERROR 1064 (42000): You have an error in your SQL syntax; check the manual that corresponds to your MySQL server version for the right syntax to use near 'test2018' at line 1
mysql> drop database test2018;
Query OK, 9 rows affected (1.09 sec)

mysql> show databases;
+--------------------+
| Database           |
+--------------------+
| information_schema |
| db1                |
| mysql              |
| performance_schema |
| test               |
| test1012           |
| zrlog              |
+--------------------+
7 rows in set (0.00 sec)

5.2 在从机器上查询库

//可以看到我们刚刚在主上面创建的库test1012就表示成功了!
mysql> show databases;
+--------------------+
| Database           |
+--------------------+
| information_schema |
| mysql              |
| performance_schema |
| test               |
| test1012           |
| test2018           |
| zrlog              |
+--------------------+
7 rows in set (0.06 sec)

//刚刚在主上面删除的test2018在从机器上也被删除了
mysql> show databases;
+--------------------+
| Database           |
+--------------------+
| information_schema |
| mysql              |
| performance_schema |
| test               |
| test1012           |
| zrlog              |
+--------------------+
6 rows in set (0.00 sec)

5.3 主从同步中常见的问题

(1)从库的IO线程无法连接,通过"show slave status G"可以查看到具体的错误信息
原因1:在主库上创建的用户授权错误,导致从库无法远程连接主库
解决办法1:在主库上通过"show grants for 'user'@'ip';"查看授权是否正确,如果错误,重新授权即可

原因2:如果是独立主机上的两个主从数据库实例,授权正确的情况下,可能是由于主库的防火墙拦截导致从库无法连接主库
解决办法2:关闭主库的防火墙,或者在主库所在服务器添加防火墙规则,允许从库的tcp连接

(2)从库启动的时候提示server-id冲突,导致无法同步主库上的数据
原因:主从库配置文件中的server-id相同了
解决办法:将主库可从库配置文件中的server-id改为不同,重新开启从库上的同步即可

(3)在从库上执行了创建库或者表的操作,然后在主库上又执行了一遍,导致同步错误,如下:

Last_SQL_Error: Error 'Can't create database 'test1'; database exists' on query. Default database: 'test1'. Query: 'create database test1'

原因:从库上创建了库,主库上再次创建,从库会将主库上的创建过程再次应用到从库,导致从库上创建同名的库,发生错误
解决办法:停止从库,然后设置sql_slave_skip_count,使其跳过同步主库创建库的操作,从下一个操作开始同步,如下:

#停止从库
mysql-server-3307> STOP SLAVE;
Query OK, 0 rows affected (0.00 sec)
#向前跳跃一步,从下一个点开始同步
mysql-server-3307> SET GLOBAL sql_slave_skip_counter =1;
Query OK, 0 rows affected (0.00 sec)
#重新开启从库上的同步
mysql-server-3307> START SLAVE ;
Query OK, 0 rows affected (0.03 sec) 
#再次查看,发现已经正常

针对直接写从库的操作,可以再从库上创建一个普通用户,授予其部分操作权限,然后设置从库的只读,通过在从库的配置文件中增加"read-only"参数来设置。但是注意,这个参数对而且只对非super用户生效,对root用户没有任何效果。

13、再生产场景下如何保证主库上的用户可以有写权限,从库上的用户只有读权限
方法1:在设置从库同步的时候,排除对mysql系统库的同步,通过在配置文件中指定binlog_ignore_db=mysql来排除不需要同步的库,或者在配置文件中指定binlog_do_db=db_name只来同步需要同步的库,然后分别在主库上创建可以写的用户,在从库上创建只能读的用户;

[mysqld]
binlog_ignore_db=mysql
binlog_do_db=user_db

方法2:在未排除任何库的情况下,先在主库上创建可以读写的用户,然后在从库中从新回收用户的写权限;
方法3:在主库和从库上创建不同的用户,然后分别授予不同的权限,使得主库只能写,从库只能读;

猜你喜欢

转载自blog.csdn.net/a1779078902/article/details/83025608
今日推荐