点击上方蓝色“程序猿DD”,选择“设为星标”

回复“资源”获取独家整理的学习资料!

作者 | Kaito

来源 | kaito-kidd.com/2020/07/02/redis-sentinel/

这篇文章,我们来看Redis是如何实现故障自动恢复的,它的实现正是要基于之前所讲的数据持久化和数据多副本而做的。

Redis作为非常火热的内存数据库,其除了具有非常高的性能之外,还需要保证高可用,在故障发生时,尽可能地降低故障带来的影响,Redis也提供了完善的故障恢复机制:哨兵。

下面就来具体来看看Redis的故障恢复是如何做的,以及其中的原理。

部署模式

Redis在部署时,可以采用多种方式部署,每种部署方式对应不同的可用级别。

单节点部署:只有一个节点提供服务,读写均在此节点,此节点宕机则数据全部丢失,直接影响业务。

master-slave方式部署:两个节点组成master-slave模式,在master上写入,slave上读取,读写分离提高访问性能,master宕机后,需要手动把slave提升为master,业务影响程度取决于手动提升master的延迟。

master-slave+哨兵方式部署:master-slave与上述相同,不同的是增加一组哨兵节点,用于实时检查master的健康状态,在master宕机后自动提升slave为新的master,最大程度降低不可用的时间,对业务影响时间较短。

从上面几种部署模式可以看出,提高Redis可用性的关键是:多副本部署 + 自动故障恢复,而多副本正是依赖主从复制。

高可用做法

Redis原生提供master-slave数据复制,保证slave永远与master数据保持一致。

在master发生问题时,我们需要把slave提升为master,继续提供服务。而这个提升新master的操作,如果是人工处理,必然无法保证及时性,所以Redis提供了哨兵节点,用来管理master-slave节点,并在master发生问题时,能够自动进行故障恢复操作。

整个故障恢复的工作,正是Redis哨兵自动完成的。

哨兵介绍

哨兵是Redis高可用的解决方案,它是一个管理多个Redis实例的服务工具,可以实现对Redis实例的监控、通知、自动故障转移。

在部署哨兵时,我们只需要在配置文件中配置需要管理的master节点,哨兵节点就可以根据配置,对Redis节点进行管理,实现高可用。

一般我们需要部署多个哨兵节点,这是因为在分布式场景下,要想确定某个机器的某个节点上否发生故障,只用一台机器去检测可能是不准确的,很有可能这两台机器的网络发生了故障,而节点本身并没有问题。

所以对于节点健康检测的场景,一般都会采用多个节点同时去检测,且多个节点分布在不同机器上,节点数量为奇数个,避免因为网络分区导致哨兵决策错误。这样多个哨兵节点互相交换检测信息,最终决策才能确认某个节点上否真正发生了问题。

哨兵节点部署并配置完成后,哨兵就会自动地对配置的master-slave进行管理,在master发生故障时,及时地提升slave为新的master,保证可用性。

那么它的工作原理上怎样的呢?

哨兵工作原理

哨兵的工作流程主要分为以下几个阶段:

  • 状态感知

  • 心跳检测

  • 选举哨兵领导者

  • 选择新的master

  • 故障恢复

  • 客户端感知新master

下面对这些阶段进行详细的介绍。

状态感知

哨兵启动后只指定了master的地址,哨兵要想在master故障时进行故障恢复,就需要知道每个master对应的slave信息。每个master可能不止一个slave,因此哨兵需要知道整个集群中完整的的拓扑关系,如何拿到这些信息?

哨兵每隔10秒会向每个master节点发送info命令,info命令返回的信息中,包含了主从拓扑关系,其中包括每个slave的地址和端口号。有了这些信息后,哨兵就会记住这些节点的拓扑信息,在后续发生故障时,选择合适的slave节点进行故障恢复。

哨兵除了向master发送info之外,还会向每个master节点特殊的pubsub中发送master当前的状态信息和哨兵自身的信息,其他哨兵节点通过订阅这个pubsub,就可以拿到每个哨兵发来的信息。

这么做的目的主要有2个:

  • 哨兵节点可以发现其他哨兵的加入,进而方便多个哨兵节点通信,为后续共同协商提供基础

  • 与其他哨兵节点交换master的状态信息,为后续判断master是否故障提供依据

心跳检测

在故障发生时,需要立即启动故障恢复机制,那么如何保证及时性呢?

每个哨兵节点每隔1秒向master、slave、其他哨兵节点发送ping命令,如果对方能在指定时间内响应,说明节点健康存活。如果未在规定时间内(可配置)响应,那么该哨兵节点认为此节点主观下线。

为什么叫做主观下线?

因为当前哨兵节点探测对方没有得到响应,很有可能这两个机器之间的网络发生了故障,而master节点本身没有任何问题,此时就认为master故障是不正确的。

要想确认master节点是否真正发生故障,就需要多个哨兵节点共同确认才行。

每个哨兵节点通过向其他哨兵节点询问此master的状态,来共同确认此节点上否真正故障。

如果超过指定数量(可配置)的哨兵节点都认为此节点主观下线,那么才会把这个节点标记为客观下线。

选举哨兵领导者

确认这个节点真正故障后,就需要进入到故障恢复阶段。如何进行故障恢复,也需要经历一系列流程。

首先需要选举出一个哨兵领导者,由这个专门的哨兵领导者来进行故障恢复操作,不用多个哨兵都参与故障恢复。选举哨兵领导者的过程,需要多个哨兵节点共同协商来选出。

这个选举协商的过程,在分布式领域中叫做达成共识,协商的算法叫做共识算法。

共识算法主要为了解决在分布式场景下,多个节点如何针对某一个场景达成一致的结果。

共识算法包括很多种,例如Paxos、Raft、Gossip算法等,感兴趣的同学可以自行搜索相关资料,这里不再展开来讲。

哨兵选举领导者的过程类似于Raft算法,它的算法足够简单易理解。

简单来讲流程如下:

  • 每个哨兵都设置一个随机超时时间,超时后向其他哨兵发送申请成为领导者的请求

  • 其他哨兵只能对收到的第一个请求进行回复确认

  • 首先达到多数确认选票的哨兵节点,成为领导者

  • 如果在确认回复后,所有哨兵都无法达到多数选票的结果,那么进行重新选举,直到选出领导者为止

选择出哨兵领导者后,之后的故障恢复操作都由这个哨兵领导者进行操作。

搜索公众号程序猿DD,回复“资源”,送你我精心整理的独家学习资料!

选择新的master

哨兵领导者针对发生故障的master节点,需要在它的slave节点中,选择一个节点来代替其工作。

这个选择新master过程也是有优先级的,在多个slave的场景下,优先级按照:slave-priority配置 > 数据完整性 > runid较小者进行选择。

也就是说优先选择slave-priority最小值的slave节点,如果所有slave此配置相同,那么选择数据最完整的slave节点,如果数据也一样,最后选择runid较小的slave节点。

提升新的master

经过优先级选择,选出了备选的master节点后,下一步就是要进行真正的主从切换了。

哨兵领导者给备选的master节点发送slaveof no one命令,让该节点成为master。

之后,哨兵领导者会给故障节点的所有slave发送slaveof $newmaster命令,让这些slave成为新master的从节点,开始从新的master上同步数据。

最后哨兵领导者把故障节点降级为slave,并写入到自己的配置文件中,待这个故障节点恢复后,则自动成为新master节点的slave。

至此,整个故障切换完成。

客户端感知新master

最后,客户端如何拿到最新的master地址呢?

哨兵在故障切换完成之后,会向自身节点的指定pubsub中写入一条信息,客户端可以订阅这个pubsub来感知master的变化通知。我们的客户端也可以通过在哨兵节点主动查询当前最新的master,来拿到最新的master地址。

另外,哨兵还提供了“钩子”机制,我们也可以在哨兵配置文件中配置一些脚本逻辑,在故障切换完成时,触发“钩子”逻辑,通知客户端发生了切换,让客户端重新在哨兵上获取最新的master地址。

一般来说,推荐采用第一种方式进行处理,很多客户端SDK中已经集成好了从哨兵节点获取最新master的方法,我们直接使用即可。

总结

可见,为了保证Redis的高可用,哨兵节点要准确无误地判断故障的发生,并且快速的选出新的节点来代替其提供服务,这中间的流程还是比较复杂的。

中间涉及到了分布式共识、分布式协商等知识,目的都是为了保证故障切换的准确性。

我们有必要了解Redis高可用的工作原理,这样我们在使用Redis时能更准确地使用它。

往期推荐

推荐一款免费的数据库管理工具,功能还很强大

盘点 Github 上的高仿 app 项目

实例告诉你如何把 if-else 重构成高质量代码!

盘点提高国内访问 GitHub 的速度的 9 种方案

这个需求很简单,明天上线没问题吧?要不要怼回去?

专注于「开发者」综合成长的深度星球

限时优惠进行中

近期系列更新

- 社会人0912期:给大家分享下我的业余生活与个人成长(一)

- 技术人0916期:技术斜杠青年要懂的一些实用能力

头条二面:宕机后,Redis如何实现快速恢复?相关推荐

  1. 慌得一逼,Kafka宕机后不再高可用?吓死宝宝了

    你知道的越多,不知道的就越多,业余的像一棵小草! 你来,我们一起精进!你不来,我和你的竞争对手一起精进! 编辑:业余草 来源:juejin.im/post/6874957625998606344 推荐 ...

  2. 如何设计不宕机的 Redis 高可用服务?

    随着业务的不断发展和扩张我们需要更加稳定和高效的 Redis 服务,这是业务发展的必然趋势也是个人能力进阶的最高境界,我们需要一个高可用的 Redis 服务,来支撑和保证业务的正常运行. 我们本文的面 ...

  3. RabbitMQ宕机后,消息100%不会丢失吗

    V-xin:ruyuanhadeng获得600+页原创精品文章汇总PDF 这篇文章,给不太熟悉MQ技术的同学,介绍一个生产环境中可能会遇到的问题. 目前为止,你的RabbitMQ部署在线上服务器了,对 ...

  4. MySQL MGR 宕机后如何开启复制

    MGR宕机后的重启,分两种情况 整个MGR集群宕机 1.首先将所有实例开启,例如 mysqld_safe --defaults-file=/etc/my.cnf1 --user=mysql & ...

  5. springboot整合redis集群master宕机后连接超时

    前提: #        本文是在确保redis集群配置正确的情况下,连接超时的解决方案. 项目登录认证使用的是sa-token(这个不重要,主要说的是springboot和redis集群),最近应甲 ...

  6. 04 | 内存快照:宕机后, Redis 如何实现快速恢复

    文章目录 1. RDB内存快照的局限性 2. 给哪些内存数据做快照 3. 快照时数据能修改吗 4. 可以每秒做一次快照吗 4. 数据快速恢复 Redis 一另一种种持久化方法:内存快照.所谓内存快照, ...

  7. 宕机后,redis如何实现快速恢复?(RDB 内存快照)

    AOF 记录的是操作命令,而不是实际的数据,所以使用 AOF 方法进行故障恢复的时候,需要逐一把操作日志都执行一遍.如果操作日志非常多,redis 就会恢复得很缓慢,影响到正常使用.所以,redis ...

  8. 内存快照:宕机后,Redis如何实现快速恢复?

    上节课,我们学习了Redis避免数据丢失的AOF方法.这个方法的好处,是每次执行只需要记录操作命令,需要持久化的数据量不大.一般而言,只要你采用的不是always的持久化策略,就不会对性能造成太大影响 ...

  9. 05 _ 内存快照:宕机后,Redis如何实现快速恢复?

    用AOF方法进行故障恢复的时候,需要逐一把操作日志都执行一遍.如果操作日志非常多,Redis就会恢复得很缓慢,影响到正常使用.这当然不是理想的结果.那么,还有没有既可以保证可靠性,还能在宕机时实现快速 ...

最新文章

  1. Html.DropDownListFor练习(2)
  2. Android-Spinner的使用以及两种适配器
  3. 天大和武大计算机考研,985大学排名出炉,天大和武大并列第10,榜首是哪所?...
  4. 安装 | MatlabR2019b: License Manager Error -8. License checkout failed.
  5. ArcEngine中使用上下左右键移动地图
  6. 前端导出excel文件带样式_vue前端使用xlsx导出数据到excel中--最简单的方式
  7. Java统计文件行数
  8. 简单干净的C#方法设计案例:SFCUI.AjaxValue()之二
  9. Codeforces Round #441 (Div. 2, by Moscow Team Olympiad)
  10. html左侧浮动广告代码,Html+CSS浮动的广告条实现分解
  11. Java是什么?Java到底能干嘛?
  12. 隐身术——使用Tor匿名网络与proxychains构建SOCKS代理链IP跳板,在***测试与******时销声匿迹...
  13. 保护你的隐私,五种控制Android应用的权限的方法
  14. 信用卡3D验证相关资料
  15. 【阿拉伯数字转中文汉字工具类】
  16. Could not publish server configuration for Tomcat v8.0 Server at localhost.
  17. SSM实现物流管理系统快递
  18. 将旧硬盘放入新主机当作资料盘时,忘记查看旧电脑IP怎么办?
  19. JQ动画和特效轮播图
  20. 汽车背后那些看不见的软件系统

热门文章

  1. cmake 静态编译 简介
  2. 数据段、数据报、数据包、帧的区别与联系
  3. alpine linux 简介(面向安全应用的发行版)apk
  4. python Selenium 常见操作 元素定位
  5. w​i​n​8​.1​无​线​上​网​ ​B​r​o​a​d​c​o​m​ ​8​0​2​.​1​1​n​ ​受​限​问​题
  6. (C++)从本机获取WMI数据.
  7. 在VS2010平台上创建并使用dll
  8. Spark编程基础(Python版)
  9. Python学习之While--break
  10. 临时内核页表的建立过程