Redis集群:哨兵机制配置

前置redis单例基本搭建参考博客:redis基础服务搭建

redis集群主要修改配置:主从复制

  • 主机配置
    复制一份redis.conf成redis-6379.conf。修改配置:

     ```
     #演示方便,开放ip连接
     bind 0.0.0.0
     #后台运行
     daemonize yes
     #pid文件
     pidfile /var/run/redis_6379.pid
     #日志文件
     logfile "6379.log"
     ```
    
  • 从库配置
    复制一份redis.conf成redis-6380.conf。修改配置:

    	#设置所有ip都可访问
    	bind 0.0.0.0
    	#端口
    	port 6380
    	#是否后台方式启动
    	daemonize yes
    	#每个服务一个pid,存放地址
    	pidfile /var/run/redis_6380.pid
    	#日志文件设置
    	logfile "6380.log"
    	#slaveof表示作为从库的配置,设置主库地址端口(主写从复制读)
    	slaveof 127.0.0.1 6379
    	#主库密码(没有设置不用写)
    	requirepass 654321
    	#从库只能读不能写(主从配置)
    	slave-read-only yes
    	#单台服务器做集群需要修改,名称不能一致
    	dbfilename dump-6379.rdb
    

    这里注意如果有密码需要配置requirepass属性,否则redis日志中会报错权限验证问题

  • 启动服务(进入redis根目录)执行命令:我这里文件名为redis-6379.conf、redis-6380.conf、redis-6381.conf存放在根目录

    	[root@VM_235_253_centos redis-4.0.9]# ./src/redis-server redis-6379.conf 
    	[root@VM_235_253_centos redis-4.0.9]# ./src/redis-server redis-6380.conf 
    	[root@VM_235_253_centos redis-4.0.9]# ./src/redis-server redis-6381.conf 
    
  • 查看redis的信息 查看redis的信息
    主库信息

    [root@VM_235_253_centos redis-4.0.9]# ./src/redis-cli -p 6379 -a 654321 info replication# Replication
    

    其中-p 6379表示指定端口
    -a 654321表示指定端口的密码,没有可以不加此参数
    replication表示主从的信息

    	# Replication
    	#主库
    	role:master
    	#2从库
    	connected_slaves:2
    	slave0:ip=119.29.76.169,port=6381,state=online,offset=207209,lag=1
    	slave1:ip=119.29.76.169,port=6380,state=online,offset=207209,lag=1
    	master_replid:59f3ac708c36d91887f61d92d48a0ea8ac397fe5
    	master_replid2:0000000000000000000000000000000000000000
    	master_repl_offset:207209
    	second_repl_offset:-1
    	repl_backlog_active:1
    	repl_backlog_size:1048576
    	repl_backlog_first_byte_offset:1
    	repl_backlog_histlen:207209
    

    查看6380从库信息

    	[root@VM_235_253_centos redis-4.0.9]# ./src/redis-cli -p 6380 -a 654321 info replication 
    	# Replication
    	#从库
    	role:slave
    	#主库地址
    	master_host:119.29.76.169
    	#主库端口
    	master_port:6379
    	master_link_status:up
    	master_last_io_seconds_ago:1
    	master_sync_in_progress:0
    	slave_repl_offset:233021
    	slave_priority:100
    	slave_read_only:1
    	connected_slaves:0
    	master_replid:59f3ac708c36d91887f61d92d48a0ea8ac397fe5
    	master_replid2:0000000000000000000000000000000000000000
    	master_repl_offset:233021
    	second_repl_offset:-1
    	repl_backlog_active:1
    	repl_backlog_size:1048576
    	repl_backlog_first_byte_offset:1
    	repl_backlog_histlen:233021
    

配置哨兵:

  • 复制根目录下sentinel.conf配置文件

  • 修改主要配置

    			#设置哨兵服务端口
    			port 26379
    			#设置后台启动
    			daemonize yes
    			#文件地址存放地址
    			dir /opt/redis-4.0.11/data
    			#Sentinel去监视一个名为mymaster 的主redis实例,这个主实例的IP地址为本机地址127.0.0.1,端口号为6379,而将这个主实例判断为失效至少需要2个 Sentinel进程的同意,只要同意Sentinel的数量不达标,自动failover就不会执行
    			sentinel monitor mymaster 127.0.0.1  6379 2
    			#设置连接master和slave时的密码,注意的是sentinel不能分别为master和slave设置不同的密码,因此master和slave的密码应该设置相同。
    			# sentinel auth-pass <master-name> <password>
    			#指定了Sentinel认为Redis实例已经失效所需的毫秒数。当实例超过该时间没有返回PING,或者直接返回错误,那么Sentinel将这个实例标记为主观下线。只有一个 Sentinel进程将实例标记为主观下线并不一定会引起实例的自动故障迁移:只有在足够数量的Sentinel都将一个实例标记为主观下线之后,实例才会被标记为客观下线,这时自动故障迁移才会执行
    			sentinel down-after-milliseconds mymaster 30000
    			#指定了在执行故障转移时,最多可以有多少个从Redis实例在同步新的主实例,在从Redis实例较多的情况下这个数字越小,同步的时间越长,完成故障转移所需的时间就越长
    			sentinel parallel-syncs mymaster 1
    			#如果在该时间(ms)内未能完成failover操作,则认为该failover失败
    			sentinel failover-timeout mymaster 180000
    			#指定sentinel检测到该监控的redis实例指向的实例异常时,调用的报警脚本。该配置项可选,但是很常用
    			# sentinel notification-script <master-name> <script-path>
    
  • 启动哨兵:两个配置文件在根目录分别为sentinel-26379.conf、sentinel-26380.conf

    [root@VM_235_253_centos redis-4.0.9]# ./src/redis-sentinel sentinel-26379.conf 
    [root@VM_235_253_centos redis-4.0.9]# ./src/redis-sentinel sentinel-26380.conf 
    

Spring boot 配置:

  • 引入redis包

     <dependency>
    	            <groupId>org.springframework.boot</groupId>
    	            <artifactId>spring-boot-starter-data-redis</artifactId>
     </dependency>
    
  • application.yml Spring配置

    spring:
     redis:
       #有密码则需要设置
       password: 654321
    #这里只需要配置哨兵即可
       sentinel:
         master: mymaster
         nodes: 119.xx.xx.xxx:26379,119.xx.xx.xxx:26380
    
  • redis序列化

    /**
     * redis序列化配置
     * @author 50238
     */
    @Configuration
    public class RedisConfig {
        /**
         * redisTemplate 序列化使用的jdkSerializeable, 存储二进制字节码, 所以自定义序列化类
         *
         * @param redisConnectionFactory
         * @return
         */
        @Bean
        public RedisTemplate<Object, Object> redisTemplate(RedisConnectionFactory redisConnectionFactory) {
            RedisTemplate<Object, Object> redisTemplate = new RedisTemplate<>();
            redisTemplate.setConnectionFactory(redisConnectionFactory);
            // 使用Jackson2JsonRedisSerialize 替换默认序列化
            Jackson2JsonRedisSerializer<Object> jackson2JsonRedisSerializer = new Jackson2JsonRedisSerializer<>(Object.class);
            ObjectMapper objectMapper = new ObjectMapper();
            objectMapper.setVisibility(PropertyAccessor.ALL, JsonAutoDetect.Visibility.ANY);
            objectMapper.enableDefaultTyping(ObjectMapper.DefaultTyping.NON_FINAL);
            jackson2JsonRedisSerializer.setObjectMapper(objectMapper);
    
            // 设置value的序列化规则和 key的序列化规则
            redisTemplate.setKeySerializer(new StringRedisSerializer());
            redisTemplate.setValueSerializer(jackson2JsonRedisSerializer);
            redisTemplate.afterPropertiesSet();
            return redisTemplate;
        }
    
    }
    

    这里我比较好奇为什么spring boot 可以直接装配就覆盖了默认的redis序列化(jdk自带的序列化),可以查看源码RedisAutoConfiguration中使用的是条件装配,主要在于这个注解@ConditionalOnMissingBean( name = {“redisTemplate”} ),当不存在redisTemplate装载时才会去装载默认的模板,这也体现了boot 的约定大于配置吧,很多地方的装配应该都是如此。

最后测试代码:

@RunWith(SpringRunner.class)
@SpringBootTest
public class BlogApplicationTests {

    @Autowired
    private RedisTemplate redisTemplate;

    @Test
    public void contextLoads() {
        ValueOperations valueOperations = redisTemplate.opsForValue();
        valueOperations.set("open", "String");
        System.out.println(valueOperations.get("open"));
    }
}

使用redis工具也可以看到确实主从做了复制,复制信息等可以从redis日志中也可以看到。
Redis哨兵-实现Redis高可用

猜你喜欢

转载自blog.csdn.net/qq_28325291/article/details/82959804