Docker安装Mysql,并搭建主从复制
1.搜索mysql镜像,拉取指定版本
docker search mysql 实际上是去https://hub.docker.com/ 搜索的,
如果直接用命令直接拉取搜索的镜像名称,如docker pull mysql,则下载的是最新版的。
如果要安装指定版本,则拉取时就需要指定版本,先到https://hub.docker.com/ ,搜索mysql,查看所有发布的版本
切换到tag标签,可以看到列出的mysql各个版本
我这里选择5.7版本的,拉取命令就是:docker pull mysql:5.7
mysql 镜像下载完成后,可以查看一下
2.安装mysql镜像
在https://hub.docker.com/_/mysql 有介绍怎么安装mysql镜像
我这里选择上面的两种分别介绍一下:
1.挂载自定义配置的方式,这种的好处时,我们可以直接在宿主机配置mysql
使用自定义MySQL配置文件启动mysql 默认情况下,MySQL的启动配置文件是/etc/mysql/my.cnf,而/etc/mysql/conf.d目录下的存在任何.cnf格式的文件时,都会使用该文件中配置项替换默认配置。 因此,如果要使用自定义配置,可以在宿主机创建一个配置文件,然后在创建容器时通过-v参数,以数据卷的方式将自定义配置挂载到mysql容器的/etc/mysql/conf.d目录下。 如,在宿主机中存在/my/mysql/conf/config-file.cnf配置文件,这时就可以通过以下方式启动MySQL容器:举例: docker run --name mysql5.7 -p 3306:3306 -v /my/mysql/data:/var/lib/mysql -v /my/mysql/conf:/etc/mysql/conf.d -e MYSQL_ROOT_PASSWORD=123456 -d mysql:5.7
2. 直接安装命令后面跟参数的方式,这种方式比较简单直接
docker run --name mysql5.7_1 -e MYSQL_ROOT_PASSWORD=123456 -p 3307:3306 -d mysql:5.7 --character-set-server=utf8mb4 --collation-server=utf8mb4_unicode_ci
我这里采取第2种方式,快速安装两台mysql
#安装第1台docker run --name mysql5.7_1 -e MYSQL_ROOT_PASSWORD=123456 -p 3307:3306 -d mysql:5.7 --character-set-server=utf8mb4 --collation-server=utf8mb4_unicode_ci #安装第2台docker run --name mysql5.7_2 -e MYSQL_ROOT_PASSWORD=123456 -p 3308:3306 -d mysql:5.7 --character-set-server=utf8mb4 --collation-server=utf8mb4_unicode_ci
查看安装后的容器,可以看到mysql状态为up,正在运行
可以在远程用命令或客户端链接任意一台,检查是否能正常连上。
用windows的命令行来连接测试,登录命令:mysql -uroot -p123456 -h 192.168.220.102 -P 3307
用Navicat客户端连接测试
至此,安装完成。
3.搭建主从复制功能
配置主从就需要修改mysql的配置文件,就需要进入mysql容器内修改配置文件
- 配置主机
这里把mysql_5.7_1这台做M主机,先进入配置它
通过docker exec -it a1c7de8adce4 /bin/bash
命令进入到Master容器内部,也可以通过docker exec -it mysql_5.7_1 /bin/bash
命令进入。a1c7de8adce4 是容器的id,而mysql_5.7_1是容器的名称。
[ ~]# docker exec -it a1c7de8adce4 /bin/bash
继续进入mysql配置目录
:/# cd /etc/mysql
查看配置文件ls -l
会看到有两个配置文件my.cnf和mysql.cnf,这个两个的关系是my.cnf是mysql.cnf的软链接,下图给予证实。所以编辑任意一个都行
但是我们在用vim时,发现容器中并没有安装,所以如果要用vim编辑,需要先安装
使用apt-get install vim
命令安装vim,又会出现如下问题
执行apt-get update
,然后再次执行apt-get install vim
即可成功安装vim。
然后vim my.cnf,增加以下配置,保存退出。
[mysqld] #这行很重要,如果my.cnf有这行则不用再重复写,如果没有则添加。 server-id=1 #服务器唯一ID log-bin=mysql-bin #开启二进制日志,主从复制的数据文件 binlog-do-db=mycat-m-s #需要同步的数据库名字 binlog_format=STATEMEN #设置logbin格式
补充一下:上面是在mysql容器中修改mysql的配置文件,需要安装vim。
其实完全可以把mysql的配置文件从容器中拷贝的宿主机,修改完成后再拷贝回mysql容器,这样更方便写。
具体步骤为:
因为进入mysql容器,我们发现真正的配置文件是 /etc/mysql/mysql.cnf,所以我们先在宿主机把此文件拷贝下来:
docker cp a1c7de8adce4:/etc/mysql/mysql.cnf /usr/local/
然后vim编辑拷贝下来的mysql.cnf:
!includedir /etc/mysql/conf.d/ !includedir /etc/mysql/mysql.conf.d/ #新增如下配置 [mysqld] server-id=1 log-bin=mysql-bin binlog-do-db=mycat_m_s binlog_format=STATEMEN
编辑保存后,再拷贝回mysql容器中,进行覆盖
docker cp mysql.cnf a1c7de8adce4:/etc/mysql/
- 配置从机
同样的方式进入从机mysql5.7_2,修改my.cnf,增加以下配置,保存退出。退出容器。
[mysqld] server-id=2 #服务器唯一ID relay-log=mysql-relay #启用
重启两台mysql容器,命令:docker restart 容器id或名称
- 登录主机mysql5.7_1,建立授权账户 slave
#在主机MySQL里执行授权命令 GRANT REPLICATION SLAVE ON *.* TO ‘slave‘@‘%‘ IDENTIFIED BY ‘123456‘;
执行完后,登录Matater查看一下用户信息:mysql> select user,host from user; 看到slave用户已经创建成功。
Master(主)和Slave(从)建立链接
登录Master,执行show master status;查看主从复制需要的配置信息
File和Position字段的值在接下来配置从机复制主机信息时会用到,所以在后面的操作完成之前,需要保证Master库不能做任何操作,否则将会引起File和Position字段的值变化。
登录slave,执行链接master配置命令
change master to master_host=‘主机的ip地址‘, master_port=端口号, master_user=‘slave‘, master_password=‘123456‘, master_log_file=‘mysql-bin.具体数字‘, master_log_pos=位置具体值,master_connect_retry=60;------------------------------------------------------------------------- 详细解释: master to master_host: Master的ip master_port:Master的端口号,因为用的是docker中的mysql,所以这里指的是宿主机映射到到mysql容器的端口 master_user:用于数据同步的用户 master_password:用于同步的用户的密码 master_log_file:指定 Slave 从哪个日志文件开始复制数据,即上文中提到的 File 字段的值 master_log_pos:从哪个 Position 开始读,即上文中提到的 Position 字段的值 master_connect_retry:如果连接失败,重试的时间间隔,单位是秒,默认是60秒
具体执行命令如下:
change master to master_host=‘192.168.220.102‘,
master_port=3307,
master_user=‘slave‘,
master_password=‘123456‘,
master_log_file=‘mysql-bin.000003‘,
master_log_pos=1821,
master_connect_retry=60;
将上面的命令复制到从mysql命令窗口执行。
查看从机状态 mysql> show slave status\G;
mysql> change master to master_host=‘192.168.220.102‘,
-> master_port=3307,
-> master_user=‘slave‘,
-> master_password=‘123456‘,
-> master_log_file=‘mysql-bin.000003‘,
-> master_log_pos=1821,
-> master_connect_retry=60;
Query OK, 0 rows affected, 2 warnings (0.00 sec)
mysql> show slave status \G;
*************************** 1. row ***************************
Slave_IO_State:
Master_Host: 192.168.220.102
Master_User: slave
Master_Port: 3307
Connect_Retry: 60
Master_Log_File: mysql-bin.000003
Read_Master_Log_Pos: 1821
Relay_Log_File: mysql-relay.000005
Relay_Log_Pos: 320
Relay_Master_Log_File: mysql-bin.000003
Slave_IO_Running: No
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: 0
Last_Error:
Skip_Counter: 0
Exec_Master_Log_Pos: 1281
Relay_Log_Space: 523
Until_Condition: None
Until_Log_File:
Until_Log_Pos: 0
Master_SSL_Allowed: No
Master_SSL_CA_File:
Master_SSL_CA_Path:
Master_SSL_Cert:
Master_SSL_Cipher:
Master_SSL_Key:
Seconds_Behind_Master: 0
Master_SSL_Verify_Server_Cert: No
Last_IO_Errno: 1236
Last_IO_Error: Got fatal error 1236 from master when reading data from binary log: ‘log event entry exceeded max_allowed_packet; Increase max_allowed_packet on master; the first event ‘mysql-bin.000003‘ at 1281, the last event read from ‘./mysql-bin.000003‘ at 123, the last byte read from ‘./mysql-bin.000003‘ at 1300.‘
Last_SQL_Errno: 0
Last_SQL_Error:
Replicate_Ignore_Server_Ids:
Master_Server_Id: 1
Master_UUID: 16d94e7b-7f17-11ea-bb5e-0242ac110003
Master_Info_File: /var/lib/mysql/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: 200417 06:26:09
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)
可以看到从机进行主从同步的两个主要线程SlaveIORunning 和 SlaveSQLRunning 都是No,正常应该是yes才对。这是因为我们还没有开启从服务器的复制功能。
使用start slave
开启主从复制,然后再次查询主从同步状态show slave status \G;
。
至此,主从复制搭建完成。
- 验证主从复制
截图如下: