
本文共 5059 字,大约阅读时间需要 16 分钟。
一、哨兵模式
(自动选举老大的模式)
1、概述
主从切换技术的方法是:当主服务器宕机后,需要手动把一台从服务器切换为主服务器,这需要人工干预,费事费力,还会造成一段时间内服务不可用。这不是一种推荐的方式。
更多时候,我们优先考虑哨兵模式
。Redis从2.8开始正式提供了Sentinel(哨兵)架构来解决这个问题。
谋权篡位的自动版
,能够后台监控主机是否故障
,如果故障了根据投票数自动
将从库
转为主库
哨兵模式是一种特殊的模式,首先Redis提供了哨兵的命令,哨兵是一个独立的进程,作为进程,它会独立运行。其原理是哨兵通过发送命令,等待Redis服务器响应,从而监控运行的多个Redis实例。
基本模型:
这里的哨兵有两个作用:↑↑↑
- 通过发送命令,让Redis服务器返回监控其运行状态,包括主服务器和从服务器
- 当哨兵检测到master宕机,会自动将slave切换成master,然后通过发布订阅模式,通知其他的从服务器,修改配置文件,让他们切换主机。
然而一个哨兵进程对Redis服务器进行监控,可能会出现问题,因此,我们可以使用多个哨兵进行监控。各个哨兵之间还会进行监控,这样子就形成了多哨兵模式
。
假设主服务器宕机,哨兵1先检测到这个结果,系统并不会马上进行failover过程,仅仅是哨兵1主观的认为主服务器不可用,这个现象称为主观下线
。
当后面的哨兵也检测到服主服务器不可用,并且数量达到一定值时,那么哨兵之间就会进行一次投票,投票的结果由一个哨兵发起,进行failover[故障转移]操作。切换成功后,就会通过发布订阅模式,让各个哨兵把自己的监控的从服务器实现切换主机,这个过程称为客观下线
。
2、测试
目前的状态:一主二从
- 创建并配置哨兵配置文件
sentinel.conf
(文件名不能有误)
#sentinel monitor 被监控名称 主机IP 主机端口 1sentinel monitor myredis 127.0.0.1 6379 1
“1”指明当有1个sentinel认为一个master失效时,master才算真正失效就发起投票换选新主机
- 启动哨兵
[root@achang bin]# redis-sentinel achangConfig/sentinel.conf
[root@achang bin]# redis-sentinel achangConfig/sentinel.conf 2627:X 11 Jan 2021 13:49:42.470 # oO0OoO0OoO0Oo Redis is starting oO0OoO0OoO0Oo2627:X 11 Jan 2021 13:49:42.470 # Redis version=5.0.7, bits=64, commit=00000000, modified=0, pid=2627, just started2627:X 11 Jan 2021 13:49:42.470 # Configuration loaded _._ _.-``__ ''-._ _.-`` `. `_. ''-._ Redis 5.0.7 (00000000/0) 64 bit .-`` .-```. ```\/ _.,_ ''-._ ( ' , .-` | `, ) Running in sentinel mode |`-._`-...-` __...-.``-._|'` _.-'| Port: 26379 | `-._ `._ / _.-' | PID: 2627 `-._ `-._ `-./ _.-' _.-' |`-._`-._ `-.__.-' _.-'_.-'| | `-._`-._ _.-'_.-' | http://redis.io `-._ `-._`-.__.-'_.-' _.-' |`-._`-._ `-.__.-' _.-'_.-'| | `-._`-._ _.-'_.-' | `-._ `-._`-.__.-'_.-' _.-' `-._ `-.__.-' _.-' `-._ _.-' `-.__.-' 2627:X 11 Jan 2021 13:49:42.472 # WARNING: The TCP backlog setting of 511 cannot be enforced because /proc/sys/net/core/somaxconn is set to the lower value of 128.2627:X 11 Jan 2021 13:49:42.480 # Sentinel ID is 6a16196babb2259f1bc1105ae6d67f06bcd257862627:X 11 Jan 2021 13:49:42.480 # +monitor master myredis 127.0.0.1 6379 quorum 12627:X 11 Jan 2021 13:49:42.481 * +slave slave 127.0.0.1:6380 127.0.0.1 6380 @ myredis 127.0.0.1 63792627:X 11 Jan 2021 13:49:42.498 * +slave slave 127.0.0.1:6381 127.0.0.1 6381 @ myredis 127.0.0.1 6379
如果Master节点宕机,这时就从 从机中随机选择一个服务器(这里有一个投票算法)
哨兵日志:↓↓↓
原来的主机重新连接,回来后,只能归并到新的主机下,当做从机:↓↓↓
原来的主机6379断开连接后,重连就成新主机6381的从机了
3、哨兵模式的优缺点
优点:
1、哨兵集群,一般基于主从复制,所有主从配置的优点,他全有【有主从复制的所有优点】
2、主从可以切换,故障可以转移,系统的可用性就会更好【系统高可用性】
3、哨兵模式就是主从模式的升级,从手动到自动,更健壮【主从模式升级,手动到自动】
缺点:
1、Redis不好在线扩容,集群容量一旦达到上限,在线扩容就十分麻烦【在线扩容麻烦】
2、实现哨兵模式的配置其实很麻烦,里面有很多选择。【配置麻烦】
二、Redis缓存穿透和雪崩(面试高频,工作常用)
服务的高可用问题
这里不细讲区分解决方案的底层
Redis缓存的使用,极大的提升了应用程序的性能和效率,特别是数据查询方面。但同时,它也带来了一些问题。其中,最要害的问题,就是数据一致性的问题,从严格意义上讲,这个问题无解。
如果对数据的一致性要求很高,那么就不能使用缓存。另外的一些典例问题就是,缓存穿透
、缓存雪崩
和缓存击穿
。目前,业界也都有比较流行的解决方案。
1、缓存穿透
穿透是没有数据,直接大量访问数据库
查不到导致的
①概念
用户想要查询
一个数据
,发现redis缓存数据库中没有
,也就是缓存没有命中,于是向持久化层数据库查询
,发现也没有,于是本次查询失败
。
当用户很多
的时候缓存都没有命中,于是都去请求了持久层数据库
,这会给持久层数据库造成很大的压力,这时就相当于缓存穿透。
②解决方案
布隆过滤器:
布隆过滤器是一种数据结构,对所有可能查询的参数以hash形式存储
,在控制层先进行效验
,不符合则丢弃
,从而避免了对底层存储系统的查询压力;
缓存空对象:
当存储层不命中后,即使返回的空对象也将其缓存起来,同时会设置一个过期时间,之后再访问这个数据将会从缓存中获取,保护了后端数据源;
缓存空对象会存在的两个问题:
- 如果空值能够被缓存起来,这就意味缓存
需要更多的空间存储更多的键
,因为这当中可能会有很多的空值的键 - 即使对控制设置了过期时间,还是会存在缓存层和储存持久层的数据会有一段时间窗口的不一致,这对于需要保持一致性的业务会有影响。【
数据会存储不一致性的可能
】
.
2、缓存击穿
击穿是一个点被穿了
查的太多了,量太大,缓冲过期后的空档期; 所有的请求砸在一个点上!
①概述
缓存击穿,指一个非常热点的key
,在不停的扛着大并发
,大并发几种对这一个点进行访问,当这个key在失效
的瞬间,持续的大并发就击穿缓存
,直接请求数据库
,就像在一个屏障上凿开一个洞。
当某个key在过期的瞬间,有大量的请求并发访问,这类数据一般是热点数据,由于缓存过期,会同时访问数据库来查询最新的数据,并且会写缓存,会导致数据库瞬间压力过大。
②解决方案
设置热点数据永不过期:
从缓存层面来看,没有设置过期时间,所以不会出现热点key过期后产生的问题。
加互斥锁:setnx…
大量的请求一个数据,缓存中没有,但是通过加分布式锁,来保证一个key只能由一个获得分布式锁的线程访问查询,其他线程只能等待
分布式锁:使用分布式锁,保证对每一个key同时只有一个线程去查询后端服务,其他线程没有获得分布式锁的权限,因此只需要等待即可。这种方式将高并发的压力转移到了分布式锁上,因此对分布式锁的考验很大。
3、缓存雪崩
雪崩是 墙(缓冲层)没了
①概念
缓存雪崩,指某一个时间段,缓存集中过期失效。
产生雪崩的原因之一,比如在写文本的时候,马上就要到双十一零点,很快就要迎来一波抢购,这波商品时间比较集中的放入了缓存,假设缓冲一个小时。那么到了凌晨一点的时候,这批商品的缓存就要都过期
了。而对这批商品的访问查询,都会落到数据库上
,对于数据库而言,就会产生周期性的压力波峰
。于是所有的请求都会达到存储持久层,存储持久层的调用量会暴增,造成存储持久层也会挂掉崩溃的情况。
其中的集中过期,倒不是非常致命,比较致命的缓存雪崩,是缓存服务器某个节点宕机或断网。因为自然形成的缓存雪崩,一定是在某个时间段集中创建缓存,这时,数据库也是可用顶住压力的。
无非就是对数据库产生周期性的压力而已。而缓存服务节点的宕机,对数据库服务器造成的压力是不可预只的,很有可能瞬间就吧数据库压垮。
②解决方案
Redis高可用:
这个思想的含义是,既然redis有可能挂掉,那我们多增设几台redis
;这样子一台挂掉之后其他的还可以继续工作,其实就是搭建集群
。
限流降级:
在缓存失效后,通过加锁
或者队列中控制读数据库写缓存的线程数量
。比如对某个key只允许一个线程查询数据和写缓存,其他线程等待。
数据预热:
在正式部署之前,我们先把可能的数据预先访问一遍
,这样子部分可能大量访问的数据
就会加载到缓冲
中。在即将发生大并发访问前手动触发加载缓存不同的key,设置不同的过期时间,让缓存失效的时间点尽量均匀
。
感谢狂神
https://www.bilibili.com/video/BV1S54y1R7SB
发表评论
最新留言
关于作者
