Redis开发运维实践高可用和集群架构与实践(四)

本文涉及的产品
云数据库 Tair(兼容Redis),内存型 2GB
Redis 开源版,标准版 2GB
推荐场景:
搭建游戏排行榜
日志服务 SLS,月写入数据量 50GB 1个月
简介:

11.1.4 高可用和异常测试

11.1.4.1 测试环境介绍

Master:192.168.2.128 (A):6379
Slave:192.168.2.129 (B):6379
Slave:192.168.2.130 (B):6379
Sentinel:三台机器的26379端口

sentinel的消息可以通过sentinel日志(/redis/log/sentinel.log)以及sentinel:hello订阅此频道进行查看。

11.1.4.2 手动切换测试

集群情况,2.128为主

发起主动切换:

127.0.0.1:26379> sentinel failover mymaster
OK

查看sentinel日志:

 [1158] 19 Jun 08:14:38.504 # Executing user requested FAILOVER of 'mymaster'
 [1158] 19 Jun 08:14:38.507 # +new-epoch 29
 [1158] 19 Jun 08:14:38.507 # +try-failover master mymaster 192.168.2.129 6379
 [1158] 19 Jun 08:14:38.581 # +vote-for-leader 7d60ccf8a9f9f81e5292a0dbde2c54c76a2bd265 29
 [1158] 19 Jun 08:14:38.581 # +elected-leader master mymaster 192.168.2.129 6379
 [1158] 19 Jun 08:14:38.581 # +failover-state-select-slave master mymaster 192.168.2.129 6379
 [1158] 19 Jun 08:14:38.655 # +selected-slave slave 192.168.2.128:6379 192.168.2.128 6379 @ mymaster 192.168.2.129 6379
 [1158] 19 Jun 08:14:38.655 * +failover-state-send-slaveof-noone slave 192.168.2.128:6379 192.168.2.128 6379 @ mymaster 192.168.2.129 6379
 [1158] 19 Jun 08:14:38.714 * +failover-state-wait-promotion slave 192.168.2.128:6379 192.168.2.128 6379 @ mymaster 192.168.2.129 6379
 [1158] 19 Jun 08:14:39.642 # +promoted-slave slave 192.168.2.128:6379 192.168.2.128 6379 @ mymaster 192.168.2.129 6379
 [1158] 19 Jun 08:14:39.642 # +failover-state-reconf-slaves master mymaster 192.168.2.129 6379
 [1158] 19 Jun 08:14:39.705 * +slave-reconf-sent slave 192.168.2.130:6379 192.168.2.130 6379 @ mymaster 192.168.2.129 6379
 [1158] 19 Jun 08:14:40.645 * +slave-reconf-inprog slave 192.168.2.130:6379 192.168.2.130 6379 @ mymaster 192.168.2.129 6379
 [1158] 19 Jun 08:14:40.645 * +slave-reconf-done slave 192.168.2.130:6379 192.168.2.130 6379 @ mymaster 192.168.2.129 6379
 [1158] 19 Jun 08:14:40.735 # +failover-end master mymaster 192.168.2.129 6379
 [1158] 19 Jun 08:14:40.735 # +switch-master mymaster 192.168.2.129 6379 192.168.2.128 6379
 [1158] 19 Jun 08:14:40.736 * +slave slave 192.168.2.130:6379 192.168.2.130 6379 @ mymaster 192.168.2.128 6379
 [1158] 19 Jun 08:14:40.743 * +slave slave 192.168.2.129:6379 192.168.2.129 6379 @ mymaster 192.168.2.128 6379
 [1158] 19 Jun 08:27:56.524 # +new-epoch 30
 [1158] 19 Jun 08:27:57.519 # +config-update-from sentinel 192.168.2.128:26379 192.168.2.128 26379 @ mymaster 192.168.2.128 6379
 [1158] 19 Jun 08:27:57.519 # +switch-master mymaster 192.168.2.128 6379 192.168.2.129 6379
 [1158] 19 Jun 08:27:57.519 * +slave slave 192.168.2.130:6379 192.168.2.130 6379 @ mymaster 192.168.2.129 6379
 [1158] 19 Jun 08:27:57.524 * +slave slave 192.168.2.128:6379 192.168.2.128 6379 @ mymaster 192.168.2.129 6379

在2.129上看,集群已经切换过来:


11.1.4.3 主实例宕测试

接上,此时master为2.129,找出redis实例的pid,然后kill:

[root@hadoop2 log]# ps -ef |grep redis-server
root 11349 1157 1 Jun18 ? 00:15:45 /usr/bin/redis-server 0.0.0.0:6379
root 14969 10433 0 08:33 pts/1 00:00:00 grep --color=auto redis-server
[root@hadoop2 log]# kill 11349

此时查看sentinel日志:

[1158] 19 Jun 08:33:57.953 # +sdown master mymaster 192.168.2.129 6379
[1158] 19 Jun 08:33:58.025 # +odown master mymaster 192.168.2.129 6379 #quorum 3/2
[1158] 19 Jun 08:33:58.025 # +new-epoch 31
[1158] 19 Jun 08:33:58.025 # +try-failover master mymaster 192.168.2.129 6379
[1158] 19 Jun 08:33:58.028 # +vote-for-leader 7d60ccf8a9f9f81e5292a0dbde2c54c76a2bd265 31
[1158] 19 Jun 08:33:58.036 # 192.168.2.130:26379 voted for 7d60ccf8a9f9f81e5292a0dbde2c54c76a2bd265 31
[1158] 19 Jun 08:33:58.037 # 192.168.2.128:26379 voted for 7d60ccf8a9f9f81e5292a0dbde2c54c76a2bd265 31
[1158] 19 Jun 08:33:58.105 # +elected-leader master mymaster 192.168.2.129 6379
[1158] 19 Jun 08:33:58.105 # +failover-state-select-slave master mymaster 192.168.2.129 6379
[1158] 19 Jun 08:33:58.183 # +selected-slave slave 192.168.2.128:6379 192.168.2.128 6379 @ mymaster 192.168.2.129 6379
[1158] 19 Jun 08:33:58.183 * +failover-state-send-slaveof-noone slave 192.168.2.128:6379 192.168.2.128 6379 @ mymaster 192.168.2.129 6379
[1158] 19 Jun 08:33:58.267 * +failover-state-wait-promotion slave 192.168.2.128:6379 192.168.2.128 6379 @ mymaster 192.168.2.129 6379
[1158] 19 Jun 08:33:59.039 # +promoted-slave slave 192.168.2.128:6379 192.168.2.128 6379 @ mymaster 192.168.2.129 6379
[1158] 19 Jun 08:33:59.040 # +failover-state-reconf-slaves master mymaster 192.168.2.129 6379
[1158] 19 Jun 08:33:59.104 * +slave-reconf-sent slave 192.168.2.130:6379 192.168.2.130 6379 @ mymaster 192.168.2.129 6379
[1158] 19 Jun 08:33:59.245 # -odown master mymaster 192.168.2.129 6379
[1158] 19 Jun 08:34:00.082 * +slave-reconf-inprog slave 192.168.2.130:6379 192.168.2.130 6379 @ mymaster 192.168.2.129 6379
[1158] 19 Jun 08:34:00.082 * +slave-reconf-done slave 192.168.2.130:6379 192.168.2.130 6379 @ mymaster 192.168.2.129 6379
[1158] 19 Jun 08:34:00.193 # +failover-end master mymaster 192.168.2.129 6379
[1158] 19 Jun 08:34:00.193 # +switch-master mymaster 192.168.2.129 6379 192.168.2.128 6379
[1158] 19 Jun 08:34:00.194 * +slave slave 192.168.2.130:6379 192.168.2.130 6379 @ mymaster 192.168.2.128 6379
[1158] 19 Jun 08:34:00.200 * +slave slave 192.168.2.129:6379 192.168.2.129 6379 @ mymaster 192.168.2.128 6379
[1158] 19 Jun 08:34:03.319 # +sdown slave 192.168.2.129:6379 192.168.2.129 6379 @ mymaster 192.168.2.128 6379

从日志中可以看出已经切换到2.128,此时在2.128上看集群状态:

目前2.128为主,2.130为从,2.129上的redis宕掉。现在重启2.129上的redis实例,启动后该节点会从原先的主变为从,并对2.128进行同步,最后达到同步状态:

查看redis.conf和redis-sentinel.conf,发现都被改写。

11.1.4.4 单从实例宕测试

接上,2.129为从,此时杀掉该进程,redis.log日志记录如下:

[14984 | signal handler] (1434674492) Received SIGTERM scheduling shutdown...
[14984] 19 Jun 08:41:32.545 # User requested shutdown...
[14984] 19 Jun 08:41:32.545 * Calling fsync() on the AOF file.
[14984] 19 Jun 08:41:32.545 * Saving the final RDB snapshot before exiting.
[14984] 19 Jun 08:41:32.580 * DB saved on disk
[14984] 19 Jun 08:41:32.580 # Redis is now ready to exit, bye bye...

此时集群正常提供对外服务,并不影响。

11.1.4.5 双从实例宕测试

接上,此时Master为2.128,还有一个活着的从2.130,集群状态如下:

此时,杀掉2.130的redis实例后,集群状态如下:

此时由于配置了最小slave个数为1,已经不满足,因此集群变为只读状态:

11.1.4.6 单sentinel宕测试

恢复集群状态,2.128为主,2.129、2.130为从。


此时,从2.128上看sentinel状态:

由于sentinel都是对等的,在此选择对2.128上的sentinel进行进程宕测试:
此时,本节点sentinel日志为:
其他节点sentinel日志为:
表示2.128上的sentnel已经宕。 此时集群读写正常,在一个sentinel宕机的基础上宕master后切换正常。

11.1.4.7 双sentinel宕测试

恢复集群状态,2.128为主,2.129、2.130为从。此时,将2.128的sentinel和2.129的sentinel都宕掉。此时主从集群读写均正常。 在双方sentinel宕机时,杀掉master,主从集群切换失效,原因是因为设置sentinel 的quorum为2,最少有两个sentinel活集群才正常切换。

11.1.4.8 master所在主机整体宕测试

恢复集群状态,2.128为主,2.129、2.130为从。此时,对2.128进行宕机测试,直接关闭电源。 主从切换至2.130,从2.129指向新的主:


sentinel日志为:

11.1.4.9 slave所在主机整体宕测试

恢复集群状态,2.128为主,2.129、2.130为从。此时直接关闭2.129,这时相当于一个redis slave进程和一个sentinel进程宕。主不受影响,并且感知到一个从已经宕机。


sentinel日志记录了此事件。

11.1.4.10 脑裂测试

恢复集群状态,2.128为主,2.129、2.130为从。首先进行一个从网络分离的测试:


此时集群状态为(从master看):

此时切断2.130这个链路,2.128和2.129分别为主从形成一个集群,2.130会失败,因为没有足够的sentinel进行投票完成failover。剩余集群如下:

第三台机器则为slave失败状态:


此时由于没有发生切换,因此对应用没有影响。

另一种情况,如果将主机网络断开,剩余两个从成为一个新的集群,其中一个从(2.129)成为主:

原来的主机则为没有slave的主:

此时由于没有可用的slave,旧主无法写入(实际上由于网络断开也根本无法访问,因此从网络和数据库本身都不具有可写性):


新主从可以接受读写请求:
此时如果旧主的网络恢复,由于它的epoch比较旧,因此会成为从,将部分同步(psync)网络宕期间产生的新数据。

从上述两种情况测试,此架构不会导致双主对外服务,也不会因为网络恢复而数据混乱。

脑裂的场景还可以进行的一个测试时多个sentinel,例如下列架构(为了便于测试在两台机器上开多端口模拟多台机器):

这个场景配置Quorum=3. 此时切断两台机器的通信网络(模拟两个机房之间通信中断),左边的机器(模拟主机房)集群不会受到影响,右边的机器(模拟灾备机房)由于不够大多数因此不会产生新的Master。

11.1.4.11 quorum测试

在一个如下的四节点环境中,

如果sentinel monitor的quorum设置为3,则宕机一台后再宕机,此时还剩余两台,存在两个sentinel,两个slave。由于quorum为3,而必须有>=max(quorum, num(sentinels)/2 +1) = max(3,2) = 3个sentinel都同意其中某一个sentinel主持failover,因此此时无sentinel可主持切换,因此测试表明,没有新的master被选出来,此时只能手动通过slaveof命令设置主从,并且手动切换(redis、sentinel和都应用不用重启):

首先修改redis:
任意选取剩余的其中一个节点进行:slaveof no one
其他节点:slaveof 192.168.145.135 6379

找一个从节点上的sentinel,进入sentinel:
redis-cli -p 26379
进行主动切换:
sentinel failover mymaster
然后再在两个sentinel上重新发现集群:
sentinel reset mymaster

检查集群状态。

如果sentinel monitor的quorum设置为2,则宕机一台后再宕机,此时还剩余两台,存在两个sentinel,两个slave。由于quorum为2,必须有>=max(quorum, num(sentinels)/2 +1)=max(2,2) =2个的sentinel都同意其中某一个sentinel主持failover,因此此时存在sentinel可主持切换,因此测试表明,新的master被选出来。

但是设置为2有一个危险就是如果出现如下的网络隔离状况:

集群就会脑裂,就会出现两个master。因此,生产上为了万无一失,宁可牺牲掉一定的高可用容错度也要避免脑裂。如果希望两台宕机依然可以切换,最好的方案不是降低quorum而是增多sentinel的个数,这个建议也是antirez在stackoverflow中回答一个人的提问时给的建议(http://stackoverflow.com/questions/27605843/redis-sentinel-last-node-doesnt-become-master#)。 如下场景测试:

此时其中两台宕机,必须有>=max(quorum, num(sentinels)/2 +1)=max(3,3) =3个的sentinel都同意其中某一个sentinel主持failover,因此此时存在sentinel可主持切换,测试结果表明此种部署方案可以正常切换。

11.1.4.12 Master hang死测试

由于我们的sentinel down-after-milliseconds为3100,即3.1s,因此在master上执行: debug sleep 3.0,系统不会切换,但是执行debug sleep 3.7或者更大的数值,系统就会判定为主sdown,进而变为odown随后发起投票切换。很难模拟取消odown的,因为时间差很短。

11.1.4.13 附:sentinel.conf被修改后的含义

port 26379 dir "/var/lib/redis/tmp" sentinel monitor mymaster 192.168.65.128 6379 2 sentinel config-epoch mymaster 18 ###确认mymater SDOWN时长 sentinel leader-epoch mymaster 18 ###同时一时间最多18个slave可同时更新配置,建议数字不要太大,以免影响正常对外提供服务 sentinel known-slave mymaster 192.168.65.129 6379 ###已知的slave sentinel known-slave mymaster 192.168.65.130 6379 ###已知的slave sentinel known-sentinel mymaster 192.168.65.130 26379 be964e6330ee1eaa9a6b5a97417e866448c0ae40 ###已知slave的唯一id sentinel known-sentinel mymaster 192.168.65.129 26379 3e468037d5dda0bbd86adc3e47b29c04f2afe9e6 ###已知slave的唯一id sentinel current-epoch 18 ####当前可同时同步的salve数最大同步阀值


本文为《Redis开发运维实践指南》内容,该书作者为黄鹏程,已授权云栖社区转载。


相关实践学习
基于Redis实现在线游戏积分排行榜
本场景将介绍如何基于Redis数据库实现在线游戏中的游戏玩家积分排行榜功能。
云数据库 Redis 版使用教程
云数据库Redis版是兼容Redis协议标准的、提供持久化的内存数据库服务,基于高可靠双机热备架构及可无缝扩展的集群架构,满足高读写性能场景及容量需弹性变配的业务需求。 产品详情:https://www.aliyun.com/product/kvstore     ------------------------------------------------------------------------- 阿里云数据库体验:数据库上云实战 开发者云会免费提供一台带自建MySQL的源数据库 ECS 实例和一台目标数据库 RDS实例。跟着指引,您可以一步步实现将ECS自建数据库迁移到目标数据库RDS。 点击下方链接,领取免费ECS&RDS资源,30分钟完成数据库上云实战!https://developer.aliyun.com/adc/scenario/51eefbd1894e42f6bb9acacadd3f9121?spm=a2c6h.13788135.J_3257954370.9.4ba85f24utseFl
相关文章
|
4天前
|
存储 SQL 监控
转转平台IM系统架构设计与实践(二):详细设计与实现
以转转IM架构为起点,介绍IM相关组件以及组件间的关系;以IM登陆和发消息的数据流转为跑道,介绍IM静态数据结构、登陆和发消息时的动态数据变化;以IM常见问题为风景,介绍保证IM实时性、可靠性、一致性的一般方案;以高可用、高并发为终点,介绍保证IM系统稳定及性能的小技巧。
19 6
|
24天前
|
存储 缓存 关系型数据库
社交软件红包技术解密(六):微信红包系统的存储层架构演进实践
微信红包本质是小额资金在用户帐户流转,有发、抢、拆三大步骤。在这个过程中对事务有高要求,所以订单最终要基于传统的RDBMS,这方面是它的强项,最终订单的存储使用互联网行业最通用的MySQL数据库。支持事务、成熟稳定,我们的团队在MySQL上有长期技术积累。但是传统数据库的扩展性有局限,需要通过架构解决。
65 18
|
1月前
|
搜索推荐 NoSQL Java
微服务架构设计与实践:用Spring Cloud实现抖音的推荐系统
本文基于Spring Cloud实现了一个简化的抖音推荐系统,涵盖用户行为管理、视频资源管理、个性化推荐和实时数据处理四大核心功能。通过Eureka进行服务注册与发现,使用Feign实现服务间调用,并借助Redis缓存用户画像,Kafka传递用户行为数据。文章详细介绍了项目搭建、服务创建及配置过程,包括用户服务、视频服务、推荐服务和数据处理服务的开发步骤。最后,通过业务测试验证了系统的功能,并引入Resilience4j实现服务降级,确保系统在部分服务故障时仍能正常运行。此示例旨在帮助读者理解微服务架构的设计思路与实践方法。
101 17
|
1月前
|
存储 消息中间件 小程序
转转平台IM系统架构设计与实践(一):整体架构设计
本文描述了转转IM为整个平台提供的支撑能力,给出了系统的整体架构设计,分析了系统架构的特性。
75 10
|
1月前
|
负载均衡 Serverless 持续交付
云端问道9期实践教学-省心省钱的云上Serverless高可用架构
详细介绍了云上Serverless高可用架构的一键部署流程
57 10
|
4月前
|
运维 Linux Apache
,自动化运维成为现代IT基础设施的关键部分。Puppet是一款强大的自动化运维工具
【10月更文挑战第7天】随着云计算和容器化技术的发展,自动化运维成为现代IT基础设施的关键部分。Puppet是一款强大的自动化运维工具,通过定义资源状态和关系,确保系统始终处于期望配置状态。本文介绍Puppet的基本概念、安装配置及使用示例,帮助读者快速掌握Puppet,实现高效自动化运维。
97 4
|
25天前
|
监控 运维
HTTPS 证书自动化运维:https证书管理系统- 自动化监控
本文介绍如何设置和查看域名或证书监控。步骤1:根据证书状态选择新增域名或证书监控,线上部署推荐域名监控,未部署选择证书监控。步骤2:查询监控记录详情。步骤3:在详情页查看每日定时检测结果或手动测试。
HTTPS 证书自动化运维:https证书管理系统- 自动化监控
|
25天前
|
Linux 持续交付 调度
HTTPS 证书自动化运维:https证书管理系统-自动化部署
本指南介绍如何部署Linux服务器节点。首先复制生成的Linux脚本命令,然后将其粘贴到目标服务器上运行。接着刷新页面查看节点记录,并点击“配置证书”选择证书以自动部署。最后,节点部署完成,后续将自动调度,无需人工干预。
HTTPS 证书自动化运维:https证书管理系统-自动化部署
|
25天前
|
运维
HTTPS 证书自动化运维:https证书管理系统之自动化签发
通过访问【https://www.lingyanspace.com】注册账户,进入证书服务菜单并新增证书。填写域名(单域名、多域名或泛域名),创建订单后添加云解析DNS记录进行质检。确认完成后可下载证书,并支持后续查看、更新和定时更新功能。证书过期前15天自动更新,需配置邮箱接收通知。
HTTPS 证书自动化运维:https证书管理系统之自动化签发
|
1月前
|
人工智能 运维 监控
AI辅助的运维流程自动化:实现智能化管理的新篇章
AI辅助的运维流程自动化:实现智能化管理的新篇章
515 22