redis的复制就是Master(主机)和Slave(副机),即主从复制,读写分离。主机数据更新后根据相关布置和策略,自动同步到副机。Master以写为主,slave以读为主,从库没有写的权限
前期准备
因为学习所用,所以采用的是端口的形式。一个不同的端口代表一个一台机
虽然我在window上演示,但是步骤尽量靠近linux
- 首先在你的工作路径下配置三个redis的配置文件。
我们以6379为主机,修改6380和6381的配置文件,主要修改端口和一些文件名。
修改端口,避免端口占用
修改RDB文件名
修改AOF文件名
然后打开6个命令行,三个作为服务器,三个作为客户端,为了方便查看,摆放成这样
首先,是6个命令行都进入你的工作目录。
三个服务器命令行分别输入
redis-server.exe redis.6379.conf
redis-server.exe redis.6380.conf
redis-server.exe redis.6381.conf
-
:
- 请注意,也许你会报没有redis-server.exe的错误,这是因为你当前目录并没有redis-server.exe的原因,只需要你在环境变量中配置redis安装目录即可,详细在基础篇有讲
三个客户端命令分别输入
redis-cli.exe -p 6379
redis-cli.exe -p 6380
redis-cli.exe -p 6381
如果六个命令行都如基础篇一样正常启动,即准备工作已完成
使用redis的主从复制相关知识
- redis的复制都是只配从库,不配主库的。
- redis的从库使用命令
- info replication可以查看当前库的身份
slaveof 主库ip 主库端口
注意!从库每次与主库master断开之后,都需要重新使用该命令进行连接,除非你在配置文件中有配置。如何在配置文件中配置,之后会说
redis 主从复制的模式措施
- 中心化,一主两仆
- 去中心化,薪火相传
- 手动式,反客为主
自动式,哨兵模式
中心化,一主两仆
该措施建立在只有一个master和众多slave的情况下,所有slave受master管理。
示例
以6379端口为主库master,6380和6381为从库slave。所以我们需要在6380和6381端口的页面输入
slaveof 127.0.0.1 6379
当输入完成,我们对三个客户端窗口分别输入命令,会看到相关信息
info replication
我们可以看到6380和6381已经成为slaver,6379成为了master,而且6379窗口还出现slave的相关信息..
去中心化,薪火相传
虽然一主两仆已经不错,但是由于只有一个master,当slave一多,对于master还是相当有压力。而且中心化意味着负责写的master只有一个,效率可能较低。
所以有了去中心化这个概念,上一个Slave可以是下一个slave的Master,Slave同样可以接收其他slaves的连接和同步请求,那么该slave作为了链条中下一个的master,可以有效减轻master的写压力
示例
目前,我们有两个slave和一个master,我们现在要进行中途转向,对6381重新分配master。那么6381会清除之前数据,重新建立拷贝最新的
在6381窗口输入
slaveof 127.0.0.1 6380
当输入完成,我们再对三个客户端窗口分别输入info replication命令,
我们可以看到,原本是master的6379现在只有一个6380的slave,6380端口既是slave,又是master,最后6381端口的master是6380
手动式,反客为主
好像去中心化已经相当不错了,但是还有问题,如果master因为意外出现故障退出了怎么办?
我们知道,slave退出的话,重新进入要重新指定master后才能受它再次管理。那么master关闭后呢?master关闭后的话,slave会依旧受master管理,但是因为没有master,意味着不会有写的操作,这不符合我们的要求。我们需要在master出现意外关闭后,有一个slave站起来,成为master
示例
为了方便演示,我们把去中心化改为中心化,让6381成为6379master的slave,然后对6379窗口输入exit,使其退出。然后我们会发现,6380和6381事实上还是接受6379管理,等待它重新归来。但现在我们不想让这个集群没有master,我们对6380输入命令,让它成为master,但是它只是光杆司令
slaveof no one
这条命令的功能是使当前数据库停止与其他数据库的同步,转成主数据库
然后我们使用info replication查看信息
但对于6381来说,它的上司还是6379。虽然6379已经out了,他有两个选择,认6380为上司,或者等6379回来,继续被6379管理
自动式,哨兵模式
哨兵模式,简单讲就是反客为主的自动版,因为反客为主需要我们手动去指定一个slave端口在master宕机后成为master。而哨兵模式会后台指派一个哨兵监控主机是否出先故障,如果故障了,在一个master宕机后,剩下的slave通过投票,抢夺成为master的机会。
示例
window下的哨兵和linux下的哨兵不一样,但两者都需要在你当前工作路径下创建一个sentinel.conf.
sentinel.conf里面写入
bind 127.0.0.1
port 26379
sentinel monitor myMaster 127.0.0.1 6381 1
哨兵模式默认端口为26379,现在将他绑定ip为127.0.0.1。
sentinel monitor myMaster 127.0.0.1 6381 1
sentinel monitor 自定义姓名 监控的ip 监控的端口 投票数达多少即可成为master
然后我们需要启动这个哨兵模式,再开一个cmd命令行,进入当前工作目录,在window下需要输入
redis-server.exe sentinel.conf --sentinel
在linux下需要输入
redis-sentinel sentinel.conf
当看到这个画面代表已经启动了哨兵。
然后我们开始搞破坏了,先把模式定义为一主两仆,主为6379,仆为6380和6381。然后在6379输入shutdown命令,然后再输入exit。表示6379客户端已经宕机。
然后你会看到6380和6381的服务器疯狂刷着一些命令,表示主人6379已经宕机。你在6380和6381上输入info replication看到的还是slave。
别急,我们切到哨兵模式的命令窗口,等待它们投票结果出来
结果出来了,6381成为了master。我们切到6381的窗口输入info replication,能发现6381已经成为了master,且手下还接管这6380这个slave。
如果这个时候6379又回来了呢?我们输入info replication会发现他是一个单独的master,但等哨兵反应过来后会把它编入新的master,即6380
redis 主从复制的原理
- Slave启动成功连接到master后会发送一个sync命令
- Master接到命令启动后台的存盘进程,同时收集所有接收到的用于修改数据集命令,在后台进程执行完毕之后,master将传送整个数据文件到slave,以完成一次完全同步
- 全量复制:而slave服务在接收到数据库文件数据后,将其存盘并加载到内存中。
- 增量复制:Master继续将新的所有收集到的修改命令依次传给slave,完成同步
- 但是只要是重新连接master,一次完全同步(全量复制)将被自动执行
redis 复制的缺点
由于所有的写操作都是先在Master上操作,然后同步更新到Slave上,所以从Master同步到Slave机器有一定的延迟,当系统很繁忙的时候,延迟问题会更加严重,Slave机器数量的增加也会使这个问题更加严重。