我们都学过mysql,并且经常使用,但可能不少人都没实际做过读写分离,今天使用docker跟docker-compose,进行读写分离的部署。我尽量每步都写出来,如果没写完的,我下次想起来再补。
首先,需要说明的是,我们使用的是linux系统,当然如果你使用的是windows理论上也是没问题的,不过你需要安装windows 的docker跟docker-compose
由于我这里使用的是ubuntu,因此使用apt进行安装即可
apt update
apt-get install docker
apt-get install docker-compose
如果是其他系统,请自行查找进行安装
首先,打开一个文件夹,运行一下命令,从而建立如下的目录结构
mkdir docker
mkdir docker/mysql
mkdir docker/mysql/master
mkdir docker/mysql/slave
如果下面使用vim进行文件编写,当然你也可以在windows进行编写然后拷进linux中。
然后使用vim修改my.cnf文件
vim docker/mysql/master/my.cnf
进入vim,按i进入插入模式,将一下内容复制进去,然后按ESC,输入:wq进行保存并退出
[client]
default-character-set=utf8
[mysqld]
init_connect='SET collation_connection = utf8_unicode_ci'
init_connect='SET NAMES utf8'
# 设置服务端字符集
character-set-server=utf8
collation-server=utf8_unicode_ci
# 忽略客户端的字符集,使用服务端的
skip-character-set-client-handshake
# 跳过域名解析,使外网连接mysql速度变快
skip-name-resolve
# 设置服务的id,每个服务都不同,这里设置为1
server_id=1
log-bin=mysql.bin
# 只读选项,如果是从库,改为1
read-only=0
# 设置那些库使用binlog,这里使用test
binlog-do-db=test
binlog-ignore-db=mysql
# 不复制系统库
replicate-ignore-db=mysql
replicate-ignore-db=sys
replicate-ignore-db=information_schema
replicate-ignore-db=performance_schema
同理,修改从库的mysql配置文件
vim docker/mysql/slave/my.cnf
跟刚才一样按i,复制后保存退出
[client]
default-character-set=utf8
[mysqld]
init_connect='SET collation_connection = utf8_unicode_ci'
init_connect='SET NAMES utf8'
# 设置服务端字符集
character-set-server=utf8
collation-server=utf8_unicode_ci
# 忽略客户端的字符集,使用服务端的
skip-character-set-client-handshake
# 跳过域名解析,使外网连接mysql速度变快
skip-name-resolve
# 设置服务的id,每个服务都不同,这里设置为1
server_id=2
log-bin=mysql.bin
# 只读选项,如果是从库,改为1
read-only=1
# 设置那些库使用binlog,这里使用test
binlog-do-db=test
binlog-ignore-db=mysql
# 不复制系统库
replicate-ignore-db=mysql
replicate-ignore-db=sys
replicate-ignore-db=information_schema
replicate-ignore-db=performance_schema
使用
vim docker/mysql/master/Dockerfile
修改主库的Dockerfile文件,然后保存退出
FROM mysql:5.7
WORKDIR /
COPY docker/mysql/master/my.cnf /etc/my.cnf
使用
vim docker/mysql/slave/Dockerfile
修改从库的Dockerfile文件,并进行保存,文件如下
FROM mysql:5.7
WORKDIR /
COPY docker/mysql/slave/my.cnf /etc/my.cnf
最后,编写docker-compose.yml文件
vim docker-compose.yml
文件如下:
version: '2'
services:
mysql-master:
environment:
- MYSQL_ROOT_PASSWORD=root
- MYSQL_ROOT_HOST=%
ports:
- "3307:3306"
links:
- mysql-slave
volumes:
- /data/mysql_gmall/master/conf:/etc/mysql/conf
- /data/mysql_gmall/master/log:/var/log/mysql
- /data/mysql_gmall/master/data:/var/lib/mysql
build:
context: .
dockerfile: ./docker/mysql/master/Dockerfile
mysql-slave:
environment:
- MYSQL_ROOT_PASSWORD=root
- MYSQL_ROOT_HOST=%
ports:
- "3308:3306"
volumes:
- /data/mysql_gmall/slave/conf:/etc/mysql/conf
- /data/mysql_gmall/slave/log:/var/log/mysql
- /data/mysql_gmall/slave/data:/var/lib/mysql
build:
context: .
dockerfile: ./docker/mysql/slave/Dockerfile
需要知道的是,我们使用了本机的3307跟3308端口映射了主机跟从库的mysql端口,如果您的端口被占用,记得修改一下上面的ports下的数值
使用以下命令进行运行跟建立
docker-compose build
docker-compose up
应该会自动下载镜像并运行,如果下载太慢,就请百度一下修改docker的镜像源,这里不再多说。
这样我们的主库跟从库就跑起来了
首先进入主库进行配置,注意运行下面的命令
你会看到以下的结果,由于我的目录是mydocker目录,因此前缀是mydocker,你们改成对应的IMAGE下的名字就行了
zhensh@zhensh-VirtualBox:~/mydocker$ docker ps
CONTAINER ID IMAGE COMMAND CREATED STATUS PORTS NAMES
b0d84f3f21ff mydocker_mysql-master "docker-entrypoint.s…" 4 hours ago Up 4 hours 33060/tcp, 0.0.0.0:3307->3306/tcp mydocker_mysql-master_1
00eb8b5ede84 mydocker_mysql-slave "docker-entrypoint.s…" 4 hours ago Up 4 hours 33060/tcp, 0.0.0.0:3308->3306/tcp mydocker_mysql-slave_1
zhensh@zhensh-VirtualBox:~/mydocker$ docker exec -it mydocker_mysql-master_1 /bin/bash
root@b0d84f3f21ff:/# mysql -u root -p
Enter password:
输入mysql密码, 密码是root
进入主库的mysql,按下面的命令运行
mysql> create user servant_1;
Query OK, 0 rows affected (0.02 sec)
mysql> GRANT REPLICATION SLAVE ON *.* TO 'servant_1'@'%' IDENTIFIED BY 'servant_password';
Query OK, 0 rows affected, 1 warning (0.10 sec)
mysql> show master status;
+--------------+----------+--------------+------------------+-------------------+
| File | Position | Binlog_Do_DB | Binlog_Ignore_DB | Executed_Gtid_Set |
+--------------+----------+--------------+------------------+-------------------+
| mysql.000003 | 843 | test | | |
+--------------+----------+--------------+------------------+-------------------+
1 row in set (0.00 sec)
记住自己的File跟Position。我这里是mysql.000003跟843。这里也可以看到我们的binlog设置的是test
退出mysql
exit
退出docker
exit
接下来进入从库,上面我们的docker有个image名字含有slave的,修改命令后运行
zhensh@zhensh-VirtualBox:~/mydocker$ docker exec -it mydocker_mysql-slave_1 /bin/bash
root@b0d84f3f21ff:/# mysql -u root -p
Enter password:
密码同样是root,进入后按下面进行运行
先运行下面命令,注意根据上面我让你们记住的的File跟Position的值进行修改,比如我我上面是mysql.000003跟843,我填入后修改
CHANGE MASTER TO
MASTER_HOST='mysql-master',
MASTER_USER='servant_1',
MASTER_PASSWORD='servant_password',
MASTER_LOG_FILE='mysql.000003',
MASTER_LOG_POS=843;
之后,开始主从备份
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: mysql-master
Master_User: servant_1
Master_Port: 3306
Connect_Retry: 60
Master_Log_File: mysql.000003
Read_Master_Log_Pos: 645
Relay_Log_File: 05daa7e2d8bc-relay-bin.000002
Relay_Log_Pos: 316
Relay_Master_Log_File: mysql.000003
Slave_IO_Running: Yes
Slave_SQL_Running: Yes
Replicate_Do_DB:
Replicate_Ignore_DB: mysql,sys,information_schema,performance_schema
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: 645
Relay_Log_Space: 530
Until_Condition: None
Until_Log_File:
Until_Log_Pos: 0
Master_SSL_Allowed: No
Master_SSL_CA_File:
Master_SSL_CA_Path:
Master_SSL_Cert:
Master_SSL_Cipher:
Master_SSL_Key:
Seconds_Behind_Master: 0
Master_SSL_Verify_Server_Cert: No
Last_IO_Errno: 0
Last_IO_Error:
Last_SQL_Errno: 0
Last_SQL_Error:
Replicate_Ignore_Server_Ids:
Master_Server_Id: 1
Master_UUID: 225d33f2-293f-11ea-a813-0242c0a86003
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:
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)
当 Slave_IO_Running
和 Slave_SQL_Running
为 Yes
时,说明同步服务正常。
OK,现在可以尝试在主库建立test库然后创建表看看从库会不会同步了。如果需要新增库只需要将my.cnf里加上binlog-do-db=库名,有多个库就多加几个。如果需要多台mysql服务器,那么就将docker跟mysql配置文件多复制一份,记得修改sever_id。顺便在主库多建立个用户