Redis集群

读/写分离

什么是读/写分离

在用户量非常庞大的时候,单台redis肯定是完全不够用的。因此更多的时候我们更希望可以读/写分离,读/写分离的前提就是读操作比写操作频繁的多,将数据放在多台服务器上那么久可以消除单台服务器的压力。

Redis主从同步
主从同步的过程

1.保证主服务器(Master)的启动
2.当从服务器启动时,发送SYNC命令给主服务器。主服务器接受到同步命令时,就是执行bgsave命令备份数据,但是主服务器并不会拒绝客户端的写操作,而是将来自客户端的写命令写入缓冲区。从服务器在未收到主服务器的备份快照文件之前,会根据配置决定使用现有数据响应客户端还是返回错误
3.当bgsave命令被主服务器执行完后,开始向从服务器发送备份文件,这个时候从服务器就会丢弃现有的所有数据,开始载入发送过来的快照文件
4.当主服务器发送完备份文件后,会将bgsave执行之后的缓存区内的写命令也发送给从服务器,从服务器完成备份文件解析后,就开始等待主服务器的后续命令
5.同步完成以后,每次主服务器完成一次写入命令,都会同时往从服务器发送同步写入命令,主从同步就完成了

配置主从同步

从机配置:
slaveof server port 设置Master的ip和端口
masterauth root 设置Master的密码

Redis哨兵模式(sentinel)
什么是哨兵模式?

主从同步有一个问题就是:当Master宕机以后需要手动的把一台Slave切换为Master,这种方式需要人工干预,费时费力。因此哨兵模式可以帮助我们解决这个问题

哨兵模式概述

哨兵是一个独立的进程
哨兵会检测多个redis服务器,包括Master和Slave。通过发送命令,让redis服务器响应,检测其运行状态。
当哨兵检测到master宕机,就会自动将slave切换成master,然后通过发布订阅模式通知其他slave修改配置文件,切换主机
为了实现哨兵的高可用,可以配置成多哨兵模式,即多个哨兵进程运行在不同的服务器上检测各个redis服务器,哨兵两两之间也会互相监控
多哨兵模式时,Master一旦宕机,哨兵1检测到这个结果,并不会马上进行故障切换,而仅仅是哨兵1主管的认为Master不可用。当其他哨兵也检测到Master不可用时,并且有一定的数量后,那么哨兵之间就会形成一次投票,投票的结果由一个哨兵发起,进行切换操作,切换完成后,就会通过发布订阅方式让各个哨兵把自己监控的服务器实现切换主机。

哨兵模式配置

配置哨兵配置文件:
redis/src/sentinel.conf
默认端口:
port 26379
内容如下:
禁止保护模式
protected-mode no
配置监听的主服务, 最后的2表示当2个或2个以上的哨兵认为主服务不可用才会进行故障切换
sentinel monitor 服务器名称(自定义) 主服务ip 端口 2
定义服务密码
sentinel auth-pass 服务器名称(和上面相同) 密码
打开服务端口:哨兵之间两两监控
vim /etc/sysconfig/iptables
service iptables restart

启动哨兵

./redis-sentinel sentinel.conf

哨兵的其他配置

sentinel down-after-milliseconds
- 指定哨兵在检测redis服务时,当redis服务在一个毫秒数内都无法回答时,单个哨兵认为的主观下线时间,默认为30秒
sentinel failover-timeout
- 指定故障切换运行的毫秒数,当超过这个毫秒数时,就认为切换故障失败,默认3分钟
sentinel notification-script
- 指定哨兵检测到redis实例异常时,调用的报警脚本

Spring中启动哨兵
<!-- 哨兵配置 -->
<bean id="sentinelConfig" 
	class="org.springframework.data.redis.connection.RedisSentinelConfiguration">
<!-- 配置master主服务的名称 -->
	<property name="master">
	   <bean class="org.springframework.data.redis.connection.RedisNode">
	    	<property name="name" value="mymaster"/>
	    </bean>
		</property>
		    <!-- 配置哨兵服务 -->
		    <property name="sentinels">
		    	<set>
		    		<bean 
		    		class="org.springframework.data.redis.connection.RedisNode">
		    			<constructor-arg name="host" value="192.168.101.153"/>
		    			<constructor-arg name="port" value="26379"/>
		    		</bean>
			    	<bean 
			    	class="org.springframework.data.redis.connection.RedisNode">
			    		<constructor-arg name="host" value="192.168.101.153"/>
			    		<constructor-arg name="port" value="26380"/>
			    	</bean>
			    	<bean 
			    	class="org.springframework.data.redis.connection.RedisNode">
			    		<constructor-arg name="host" value="192.168.101.153"/>
			    		<constructor-arg name="port" value="26381"/>
			    	</bean>
		     </set>
	</property>
</bean>
SpringBoot中启动哨兵
spring:
  redis:
    sentinel:
      master: myMaster
      nodes: 
        - 192.168.184.130:26379
        - 192.168.184.131:26379
        - 192.168.184.132:26379

Cluster模式

Cluster集群的特点

1、Client与redis节点直接连接,不需要中间proxy层.
2、redis-cluster把所有的物理节点映射到[0-16383]slot(插槽)上,cluster 负责维护
3、所有的redis节点彼此互联(PING-PONG机制),内部使用gossip二进制协议优化传输数据
4、节点的失效检测是通过集群中超过半数的节点检测失效时才生效.
问题:Redis 集群中内置了 16384 个哈希槽,那他是如何决定将key放入哪个插槽的?
- 当Redis 集群中放置一个 key-value 时,redis 先对 key 使用 crc16 算法算出一个结果,然后把结果对 16384 求余数,这样每个 key 都会对应一个编号在 0-16383 之间的哈希槽,redis 会根据节点数量大致均等的将哈希槽映射到不同的节点

Cluster集群搭建步骤

前置条件:删除redis/src下的appendonly.aof,dump.rdb,nodes-6379.conf 3个文件
1.
修改redis.conf,配置集群信息
开启集群,cluster-enabled yes
指定集群的配置文件,cluster-config-file nodes-端口.conf
2、用redis-trib.rb搭建集群
因为redis-trib.rb是用Ruby实现的Redis集群管理工具,所以我们需要先安装ruby的环境
2.1、安装ruby
yum -y install zlib ruby rubygems
2.2、安装rubygems的redis依赖
gem install -l redis-3.3.0.gem
3、安装好依赖的环境之后,我们就可以来使用脚本命令了
注意:此脚本文件在我们的解压缩目录src下
执行命令:
./redis-trib.rb create --replicas 0 192.168.10.167:6379 192.168.10.167:6380 192.168.10.167:6381 开放16379 redis端口+1W
–replicas 0:指定了从数据的数量为0
4、查看集群状态
通过客户端输入以下命令:
cluster nodes:这个命令可以查看插槽的分配情况
整个Redis提供了16384个插槽,./redis-trib.rb 脚本实现了是将16384个插槽平均分配给了N个节点。

Cluster高可用集群的搭建步骤

问题:集群中的故障检查机制
1、当集群中的节点超过半数认为该目标节点疑似下线,那么该节点就会被标记为下线;
2、当集群中的任何一个节点下线,就会导致插槽区有空档,不完整,那么该集群将不可用;
解决方案
- 在Redis集群中可以使用主从模式实现某一个节点的高可用
创建新集群,且设置为一主一备
./redis-trib.rb create --replicas 1 192.168.10.167:6379 192.168.10.167:6380 192.168.10.167:6381 192.168.10.167:6382 192.168.10.167:6383 192.168.10.167:6384

spring:
    redis:
    cluster:
      max-redirects: 0
      nodes:
        - 192.168.184.130:26379
        - 192.168.184.131:26379
        - 192.168.184.132:26379