Redis故障转移
概述
本文主要讲述了Redis故障转移的原理及过程,可与「Redis高可用架构」文章一同阅读,可更好理解相关内容,及整个Redis高可用架构的实现原理。
Leader 选举
哨兵首先进入 WATI_START
状态进行准备,等待哨兵成为哨兵集群的 Leader 才有资格进行故障转移。如果在超时时间之内哨兵都没有成为 Leader,则哨兵会调用 sentinelAbortFailover()
函数并结束本次故障转移。
当哨兵想要进行故障转移,首先需要得到多数哨兵的支持才能进行。而且,同一时间可能会有多个哨兵发起故障转移,所以故障转移前需要进行一轮竞选,得到多数选票的哨兵会被称为 Leader,只有 Leader 才能进行故障转移。
选举原理
Redis 的 Leader 选举使用的是 Raft 算法,因此 Leader 选举的流程是相同的,具体可见:【分布式】Raft 算法 - Leader 选举。
哨兵属性
根据 Raft 算法,每个哨兵需要存储两个信息,是当前任期和心仪候选人,在 Redis 定义为 current_epoch
和 leader
,leander
字段用于存储心仪候选人的 runId
。
投票请求
同时,哨兵的投票请求依旧沿用 SENTINEL is-master-down-by-addr
指令,但此时除了附上自己的 Epoch 之外,还会在参数中带上自己的 runId
,标志投票的发起人。如:
SENTINEL is-master-down-by-addr 172.26.0.101 6379 4 9effe0cdc338e245391055caa45a05adf61fed37
投票方法
根据 Raft 算法,哨兵的投票原则就是:leader
字段是谁的 ID,就投给谁。
- 当哨兵要参加竞选,就会将自己的
current_epoch
字段加一,并将leader
字段指向自己。- 当哨兵接收到投票请求,如果请求的
epoch
小于等于哨兵自身的current_epoch
,就投给自己leader
字段所指的哨兵。如果大于自身的current_epoch
,就将更新自己的leader
字段为请求中的runId
,再将票投给对方。- 根据第一点和第二点,如果竞选哨兵收到了其他哨兵的投票请求,此时对方
epoch
与自己相等,永远都只会投给自己。
因此,同一轮 Epoch 的竞选中,不参选的哨兵会一直投给第一个发给它请求的哨兵。参选的哨兵会一直投给自己。这样,保证了同一轮 Epoch 竞选中,每个投票人只能投给一个人,保证了投票的正确性和公平性。
选举过程
总结哨兵的具体选举过程为:
- 哨兵确认主节点
odown
后,将自身current_epoch
加一,将leader
指向自己,并向其他哨兵发送投票请求。- 其他哨兵接收到投票请求,判断请求中的
epoch
是否大于自己的current_epoch
: 大于则更新current_epoch
并将leader
指向发送方,然后投票给发送方。 小于或等于则将票投给自己leader
字段指向的哨兵(可能是它自己)。- 哨兵每收到一个回复就会将对方的投票结果存储起来,并累计自己的得票数(投给自己的选票数加一,算上自己),当自己得票数超一半且不小于
quorum
时,成为 Leader 并向所有哨兵公示投票结果。- 如果到投票计时截止,哨兵自身的累计票数还没达标,哨兵就会宣告竞选失败,并进入一段随机的等待时间,等待结束之后会再次进行选举。
- 落选可能是有其他人当选,也可能没人能达标,当哨兵不关心有没有人胜选,因为如果有晋级者,它会主动宣告成功的。
- 在等待期间如果没有任何哨兵宣布胜选,则等待时间结束后,哨兵会重新进行选举,此时回到步骤 1。
Master 选取
当选 Leader 后哨兵会进入 SELECT_SLAVE
状态,选取新的主节点。
选取新的主节点遵守以下规则:
-
排除:
- 已下线的从节点(
sdown
、odown
)。 - 连接断开的节点(
PING
超时,disconnected
状态)。 - 配置了不当 Master 的节点(
replica-priority = 0
)。 - 与宕机主节点断开时间过长的从节点(超 10 倍
down-after-milliseconds
)。
- 已下线的从节点(
-
优先级,从高到低排序:
- 优先值最高的节点(
replica-priority
最小)。 - 复制偏移量最大的节点。
- 配置了
runId
的节点。 - 随机
runId
字典序最小的节点。
- 优先值最高的节点(
如果选取失败,会隔一段时间进行重试,直到选取出新的主节点为止。
Slave 身份去除
当确定新的主节点后,哨兵会进入 SEND_SLAVEOF_NOONE
状态,撤销该节点的 Slave 状态。
1:X 19 Aug 2021 08:30:07.587 * +failover-state-send-slaveof-noone slave 172.25.0.102:6379 172.25.0.102 6379 @ mymaster 172.25.0.101 6379
哨兵会发送 slaveof NO ONE
指令给从节点,从节点接收到后会断开它与原主节点的网络连接,重置其复制 ID 并执行持久化重写,并开始将自己的复制身份转为 Master。
提升 Master
在发送指令之后,哨兵会进入 WAIT_PROMOTION
状态,等待该节点将自己提升为主节点。
1:X 19 Aug 2021 08:30:07.679 * +failover-state-wait-promotion slave 172.25.0.102:6379 172.25.0.102 6379 @ mymaster 172.25.0.101 6379
等待过程中哨兵会每隔一秒发送一次 INFO
命令给它,直到它的角色变成 Master。
配置从节点
当节点提升为 Master 之后,哨兵会进入 RECONF_SLAVES
状态,更新所有从节点的配置,让他们去复制新的 Master。
1:X 19 Mar 2024 13:30:08.374 # +promoted-slave slave 172.25.0.102:6379 172.25.0.102 6379 @ mymaster 172.25.0.101 6379
1:X 19 Mar 2024 13:30:08.374 # +failover-state-reconf-slaves master mymaster 172.25.0.101 6379
哨兵通过向从节点发送 slaveof <ip> <port>
命令即可修改从节点复制配置,并让从节点去复制新的主节点。
相关文章:
Redis故障转移
概述 本文主要讲述了Redis故障转移的原理及过程,可与「Redis高可用架构」文章一同阅读,可更好理解相关内容,及整个Redis高可用架构的实现原理。 Leader 选举 哨兵首先进入 WATI_START 状态进行准备,等待哨兵成为哨兵集群的 Leade…...
STM32学习笔记:定时器(TIM)原理与应用(详解篇)
前言 定时器是STM32微控制器中最重要且最常用的外设之一,它不仅能提供精确的定时功能,还能实现PWM输出、输入捕获、编码器接口等多种功能。本文将全面介绍STM32的通用定时器,包括其工作原理、配置方法和典型应用。 一、STM32定时器概述 定…...
JAVA获取ES连接并查询所有数据
我们的项目要获取es连接,新版本和旧版本有不小的区别,在8.17.0版本使用的是 ElasticsearchClient <dependency><groupId>co.elastic.clients</groupId><artifactId>elasticsearch-java</artifactId><version>8.17…...

408第一季 - 数据结构 - 线性表
只能用C/C! 顺序表 闲聊 线性表的逻辑顺序和物理顺序相同 都是1234 顺序表的优点: 随机访问,随机访问的意思是访问的时间 和位置没有关系,访问下标1和100一样的,更深层就是直接计算 a100 * 数组大小,随便…...

第23讲、Odoo18 邮件系统整体架构
目录 Odoo 邮件系统整体架构邮件发送方式邮件模板配置SMTP 邮件服务器配置邮件发送过程开发中常见邮件发送需求常见问题排查提示与最佳实践完整示例:审批通过自动发邮件门户表单自动邮件通知案例邮件队列与异步发送邮件添加附件邮件日志与调试多语言邮件模板邮件安…...
【QT面试题】(三)
文章目录 Qt信号槽的优点及缺点Qt中的文件流和数据流区别?Qt中show和exec区别QT多线程使用的方法 (4种)QString与基本数据类型如何转换?QT保证多线程安全事件与信号的区别connect函数的连接方式?信号与槽的多种用法Qt的事件过滤器有哪些同步和…...
DeepSeek09-open-webui使用
Open WebUI 完全指南:从安装到知识库搭建与异常处理 最后更新:2025年6月7日 | 适用版本:Open WebUI v0.6.x 一、安装部署 1.1 系统要求 **Python 3.12 **(严格版本要求,更高版本3.13不兼容)Node.js 20.x内…...

HarmonyOS:Counter计数器组件
一、概述 计数器组件,提供相应的增加或者减少的计数操作。 说明 该组件从API Version 7开始支持。后续版本如有新增内容,则采用上角标单独标记该内容的起始版本。 二、属性 除支持通用属性外,还支持以下属性。 enableInc enableInc(value: b…...
数据类型 -- 字符
在C中,字符型(char)用于存储单个字符,如字母、数字、符号等。字符型是最基本的数据类型之一,常用于处理文本、字符数组(字符串)等场景。 1. 基本类型 • char:标准字符类型&#x…...
WordZero:让Markdown与Word文档自由转换的Golang利器
在日常工作中,我们经常需要在Markdown和Word文档之间进行转换。Markdown方便编写和版本控制,而Word文档更适合正式的商务环境。作为一名Golang开发者,我开发了WordZero这个库,专门解决这个痛点。 项目背景 GitHub仓库࿱…...

sqlsugar WhereIF条件的大于等于和等于查出来的坑
一、如下图所示,当我用 .WhereIF(input.Plancontroltype > 0, u > u.Plancontroltype (DnjqPlancontroltype)input.Plancontroltype) 这里面用等于的时候,返回结果一条数据都没有。 上图中生成的SQL如下: SELECT id AS Id ,code AS …...

Pandas 技术解析:从数据结构到应用场景的深度探索
序 我最早用Python做大数据项目时,接触最早的就是Pandas了。觉得对于IT技术人员而言,它是可以属于多场景的存在,因为它的本身就是数据驱动的技术生态中,对于软件工程师而言,它是快速构建数据处理管道的基石࿱…...

数据库系统概论(十七)超详细讲解数据库规范化与五大范式(从函数依赖到多值依赖,再到五大范式,附带例题,表格,知识图谱对比带你一步步掌握)
数据库系统概论(十七)超详细讲解数据库规范化与五大范式(从函数依赖到多值依赖,再到五大范式,附带例题,表格,知识图谱对比带你一步步掌握) 前言一、为什么需要规范化1. 我们先想一个…...
[c#]判定当前软件是否用管理员权限打开
有时一些软件的逻辑中需要使用管理员权限对某些文件进行修改时,那么该软件在执行或者打开的场合,就需要用使用管理员身份运行才能达到效果。那么在c#里,如何判定该软件是否是对管理员身份运的呢? 1.取得当前的windows用户。 2.取得…...

并发编程实战(生产者消费者模型)
在并发编程中使用生产者和消费者模式能够解决绝大多数的并发问题。该模式通过平衡生产线程和消费线程的工作能力来提高程序整体处理数据的速度。 生产者和消费者模式: 在线程的世界中生产者就是产生数据的线程,而消费者则是消费数据的线程。在多线程开…...
分布式微服务系统架构第144集:FastAPI全栈开发教育系统
加群联系作者vx:xiaoda0423 仓库地址:https://webvueblog.github.io/JavaPlusDoc/ https://1024bat.cn/ https://github.com/webVueBlog/fastapi_plus https://webvueblog.github.io/JavaPlusDoc/ 使用docker搭建常用开发环境 docker安装mysql docker ru…...
el-tabs 切换时数据不更新的问题
最近业务需求,需要在页面中使用tabs,使用过程中出现tabs切换,数据不更新的问题,以下是思路和解决办法。 Vue 会追踪你在模板中绑定的数据,并在数据发生变化时重新渲染相应的部分。但在使用 el-tabs 时,有时…...

git小乌龟不显示图标状态解决方案
第一步 在开始菜单的搜索处,输入regedit命令,打开注册表。 第二步 在注册表编辑器中,找到HKEY_LOCAL_MACHINE\SOFTWARE\Microsoft\Windows\CurrentVersion\Explorer\ShellIconOverlayIdentifiers 这一项。 第三步 让Tortoise相关的项目排在前…...

获取 OpenAI API Key
你可以按照以下步骤来获取 openai.api_key,用于调用 OpenAI 的 GPT-4、DALLE、Whisper 等 API 服务: 🧭 获取 OpenAI API Key 的步骤: ✅ 1. 注册或登录 OpenAI 账号 打开 https://platform.openai.com/ 使用你的邮箱或 Google/…...

【Android基础回顾】五:AMS(Activity Manager Service)
Android 的 AMS(Activity Manager Service)是 Android 系统中的核心服务之一,负责管理整个应用生命周期、任务栈、进程和四大组件(Activity、Service、BroadcastReceiver、ContentProvider)的运行。它运行在系统进程 s…...

pycharm中提示C++ compiler not found -- please install a compiler
1.最近用pycharm编译一个开源库,编译的依赖c compiler 2.单单使用pycharm编译,编译器报错C compiler not found – please install a compiler 3.需要在配置环境中引入对应库 4.从新编译后没有提示:C compiler not found – please install a compiler错误。...
类型别名与类型自动推导
类型别名与类型的自动推导 类型别名 为什么要引入类型别名? 为了给类型赋予特殊含义或便于使用 典型用途 (1)增强代码可移植性 例如:size_t (在不同系统中可能是unsigned int 或 unsigned long) 首先是…...

一站式直播工具:助力内容创作者高效开启直播新时代
近年来,随着互联网技术的不断进步和短视频、直播行业的爆发式增长,越来越多的企业和个人投入到直播电商、互动娱乐、在线教育等场景。直播运营过程中,涉及到数据统计、弹幕互动、流程自动化、内容同步等诸多环节。如何提升运营效率、减少人工…...
【学习笔记】Lamba表达式[匿名函数]
【学习笔记】Lamba表达式[匿名函数] Lamba表达式格式函数模板Lamba表达式例子 Lamba表达式格式 格式: [捕获列表](参数列表) -> 返回类型 { 函数体 }1、捕获列表:指定如何访问外部变量(如 [&x] 引用捕获,[x] 值捕获&#…...
学习笔记(26):线性代数-张量的降维求和,简单示例
学习笔记(26):线性代数-张量的降维求和,简单示例 1.先理解 “轴(Axis)” 的含义 张量的 “轴” 可以理解为 维度的方向索引 。对于形状为 (2, 3, 4) 的张量,3 个轴的含义是: 轴 0(axis0&…...

以智能管理为基础,楼宇自控打造建筑碳中和新路径
在全球气候变化的严峻形势下,“碳中和”已成为各国发展的重要战略目标。建筑行业作为能源消耗与碳排放的“大户”,其运行阶段的能耗占全社会总能耗近40%,碳排放占比与之相当,实现建筑碳中和迫在眉睫。传统建筑管理模式下ÿ…...
81 实战一:给root目录扩容
添加一块100G硬盘 vgextend centos /dev/sdb1 /dev/sdc lvextend -L +120G /dev/centos/root xfs_growfs /dev/centos/root df -h 看是否扩容成功 82 实战二:给swap空间扩容 添加一块20G硬盘 fdisk -l 可以看到新添加的硬盘 vgextend centos /dev/sdd …...
1130 - Host ‘xxx.x.xx.xxx‘is not allowed to connect to this MySQL server
以下为本次问题的解决办法: 1、暂停mysql容器: docker stop mysql 2、删除mysql容器:docker rm mysql 3、查看mysql容器是否被删除:docker ps -a #没有mysql容器就是删除成功 4、run mysql容器: docker run -d --…...
HttpURLConnection实现
我有一个接口 http://ip:port/Others/airportnew/,采用post方法调用,采用body方式传值,其body内容为{"data": {"data": {"image": ""}} },现在我需要在java中调用这个接口,帮…...

day029-Shell自动化编程-计算与while循环
文章目录 1. read 交互式初始化变量1.1 案例-安装不同的软件1.2 案例-比较大小 2. 计算2.1 bc2.2 awk2.3 expr2.4 let2.5 案例-计算内存的空闲率2.6 案例-检查域名过期时间和https整数过期时间 3. 循环3.1 循环控制语句3.2 for循环-c语言格式3.3 while循环3.3.1 案例-猜数字3.3…...