springboot入门:集成redis哨兵模式,实现mybatis二级缓存

光头才能强      2022-05-17     622

关键词:

本片文章续《Spring Boot 入门(九):集成Quartz定时任务》。本文主要基于redis实现了mybatis二级缓存。较redis缓存,mybaits自带缓存存在缺点(自行谷歌)。本文是基于docker安装redis主从模式。

1.redis安装

(1)首先安装redis集群模式,建立redis目录,并编写主从模式docker-compose.yml文件

 1 version: '3.1'
 2 services:
 3   master:  
 4     image: redis
 5     container_name: redis-master
 6     ports:
 7       - 6379:6379
 8         
 9   slave1:  
10     image: redis
11     container_name: redis-slave-1
12     ports:
13       - 6380:6379
14     command: redis-server --slaveof redis-master 6379
15           
16   slave2:  
17     image: redis
18     container_name: redis-slave-2
19     ports:
20       - 6381:6379
21     command: redis-server --slaveof redis-master 6379

(2).启动 docker-compose up -d

(3).建立sentinel文件,并编写docker-compose.yml文件

 1 version: '3.1'
 2 services:
 3   sentinel1:  
 4     image: redis
 5     container_name: redis-sentinel-1
 6     ports:
 7       - 26379:26379
 8     command: redis-sentinel /usr/local/etc/redis/sentinel.conf
 9     volumes:
10       - ./sentinel1.conf:/usr/local/etc/redis/sentinel.conf
11         
12   sentinel2:  
13     image: redis
14     container_name: redis-sentinel-2
15     ports:
16       - 26380:26379
17     command: redis-sentinel /usr/local/etc/redis/sentinel.conf
18     volumes:
19       - ./sentinel2.conf:/usr/local/etc/redis/sentinel.conf
20         
21   sentinel3:  
22     image: redis
23     container_name: redis-sentinel-3
24     ports:
25       - 26381:26379
26     command: redis-sentinel /usr/local/etc/redis/sentinel.conf
27     volumes:
28       - ./sentinel3.conf:/usr/local/etc/redis/sentinel.conf
29         

从模式需要sentinel的conf文件,我创建了3个容器,所以这里需要3份(sentinel1.conf sentinel2.conf sentinel3.conf),内容是一模一样

1 port 26379
2 dir /tmp
3 sentinel monitor mymaster 217.0.0.1 6379 2
4 sentinel down-after-milliseconds rmaster 30000
5 sentinel parallel-syncs mymaster 1
6 sentinel failover-timeout mymaster 180000
7 sentinel deny-scripts-reconfig yes

(4).启动:docker-compose up -d

(5).验证redis是否已经成功启动

进入容器:docker exec -it redis-sentinel-1 /bin/bash

连接redis:redis-cli -p 26379

如下图,表示启动成功

 

也可以通过桌面客户端查看是否启动成功,如图,我使用的RedisDesktopManager客户端

 

 这里有个问题可以思考:传统的redis集群,即cluster,也有主从模式,现在为什么大家都选择sentinel主从模式?

 2.编写RedisCache工具类

网上一大堆,根据自己需要选择合适的utils(有的utils中方法很全)

  1 package com.learn.hello.system.utils;
  2 
  3 import lombok.extern.slf4j.Slf4j;
  4 import org.apache.ibatis.cache.Cache;
  5 import org.springframework.data.redis.core.RedisCallback;
  6 import org.springframework.data.redis.core.RedisTemplate;
  7 import org.springframework.data.redis.core.ValueOperations;
  8 
  9 import java.util.concurrent.TimeUnit;
 10 import java.util.concurrent.locks.ReadWriteLock;
 11 import java.util.concurrent.locks.ReentrantReadWriteLock;
 12 
 13 /**
 14  * @ClassName RedisCache
 15  * @Deccription 通过redis实现mybaits的二级缓存
 16  * @Author DZ
 17  * @Date 2020/1/12 22:41
 18  **/
 19 @Slf4j
 20 public class RedisCache implements Cache {
 21 
 22     private final ReadWriteLock readWriteLock = new ReentrantReadWriteLock();
 23     private final String id; // cache instance id
 24     private RedisTemplate redisTemplate;
 25 
 26     private static final long EXPIRE_TIME_IN_MINUTES = 30; // redis过期时间
 27 
 28     public RedisCache(String id) {
 29         if (id == null) {
 30             throw new IllegalArgumentException("Cache instances require an ID");
 31         }
 32         this.id = id;
 33     }
 34 
 35     @Override
 36     public String getId() {
 37         return id;
 38     }
 39 
 40     /**
 41      * Put query result to redis
 42      *
 43      * @param key
 44      * @param value
 45      */
 46     @Override
 47     public void putObject(Object key, Object value) {
 48         try {
 49             RedisTemplate redisTemplate = getRedisTemplate();
 50             ValueOperations opsForValue = redisTemplate.opsForValue();
 51             opsForValue.set(key, value, EXPIRE_TIME_IN_MINUTES, TimeUnit.MINUTES);
 52             log.debug("Put query result to redis");
 53         } catch (Throwable t) {
 54             log.error("Redis put failed", t);
 55         }
 56     }
 57 
 58     /**
 59      * Get cached query result from redis
 60      *
 61      * @param key
 62      * @return
 63      */
 64     @Override
 65     public Object getObject(Object key) {
 66         try {
 67             RedisTemplate redisTemplate = getRedisTemplate();
 68             ValueOperations opsForValue = redisTemplate.opsForValue();
 69             log.debug("Get cached query result from redis");
 70             return opsForValue.get(key);
 71         } catch (Throwable t) {
 72             log.error("Redis get failed, fail over to db", t);
 73             return null;
 74         }
 75     }
 76 
 77     /**
 78      * Remove cached query result from redis
 79      *
 80      * @param key
 81      * @return
 82      */
 83     @Override
 84     @SuppressWarnings("unchecked")
 85     public Object removeObject(Object key) {
 86         try {
 87             RedisTemplate redisTemplate = getRedisTemplate();
 88             redisTemplate.delete(key);
 89             log.debug("Remove cached query result from redis");
 90         } catch (Throwable t) {
 91             log.error("Redis remove failed", t);
 92         }
 93         return null;
 94     }
 95 
 96     /**
 97      * Clears this cache instance
 98      */
 99     @Override
100     public void clear() {
101         RedisTemplate redisTemplate = getRedisTemplate();
102         redisTemplate.execute((RedisCallback) connection -> {
103             connection.flushDb();
104             return null;
105         });
106         log.debug("Clear all the cached query result from redis");
107     }
108 
109     /**
110      * This method is not used
111      *
112      * @return
113      */
114     @Override
115     public int getSize() {
116         return 0;
117     }
118 
119     @Override
120     public ReadWriteLock getReadWriteLock() {
121         return readWriteLock;
122     }
123 
124     private RedisTemplate getRedisTemplate() {
125         if (redisTemplate == null) {
126             redisTemplate = SpringContextHolder.getBean("redisTemplate");
127         }
128         return redisTemplate;
129     }
130 }

3.在接口类增加redis缓存注解

@CacheNamespace(implementation = RedisCache.class)

例如:

1 @CacheNamespace(implementation = RedisCache.class)
2 public interface RoleMapper extends MyMapper<Role> {
3     List<Role> selectByCondition(ModelMap modelMap);
4 
5     Role selectById(int id);
6 
7     List<Role> selectAllRole();
8 }

这里也可以直接在MyMapper父接口中增加注解,这样,所有的接口就不需要单独增加这个注解(根据业务需要自行素选择)。

4.配置application.yml

 1 spring:
 2   redis:
# 哨兵模式推荐使用lettuce作为客户端,弃用jedis
3 lettuce: 4 # 连接池配置 5 pool: 6 # 连接池中的最小空闲连接,默认 0 7 min-idle: 0 8 # 连接池中的最大空闲连接,默认 8 9 max-idle: 8 10 # 连接池最大阻塞等待时间(使用负值表示没有限制),默认 -1ms 11 max-wait: -1ms 12 # 连接池最大连接数(使用负值表示没有限制),默认 8 13 max-active: 8 14 # 集群模式 15 # cluster: 16 # nodes: 192.168.1.12:6379,192.168.1.12:6380,192.168.1.12:6381 17 # 哨兵模式 18 sentinel: 19 master: mymaster 20 nodes: 192.168.1.12:26379,192.168.1.12:26380,192.168.1.12:26381
1 mybatis:
2   mapper-locations: classpath:mapper/*.xml
3   #  此配置的作用:xml中不用写实体类的全路径
4   type-aliases-package: com.learn.hello.modules.entity
5   #  查询的null字段也返回
6   configuration:
7     call-setters-on-nulls: true
8     #    开启二级缓存
9     cache-enabled: true

 

5.效果

当进行CURD操作时,相关的检索sql语句就会缓存到redis,如图:

 

 当再次对相关数据进行CRUD时,就会走缓存

springboot入门:集成websocket,实时显示系统日志

以前面的博客为基础,最近一篇为SpringBoot入门(十):集成Redis哨兵模式,实现Mybatis二级缓存。本篇博客主要介绍了SpringBoot集成WebSocket进行日志的推送,并实时显示在页面上。1.导入jar包第一个jar包是websocket的,第二个jar包是... 查看详情

springcloud集成redis(单机模式+哨兵模式)

下面是自己写的springcloud两种集成redis操作的方式spring-data-redis(单机和哨兵模式)RedisTemplate工具类(单机和哨兵模式)而单机部署方式和哨兵部署方式切换后,调整的点仅仅是configserver的配置http://note.youdao.com/noteshare?id=0ce02d8c8dc... 查看详情

springboot连接redis哨兵模式

...bind0.0.0.0【注】redisTemplate实际上是对其他框架的的封装,springboot2.x以上底层实现由jedis变为了lettuce。而且lettuce会根据配置自动选择是否用单机或者哨兵模式。【1】Redis哨兵模式设置密码【2】sentinel搭建redis集群经验总结【3】Spri... 查看详情

springboot集成redis基础入门(代码片段)

...式的数据备份更多redis相关文档请查看redis官方文档redis和springbootredis在springboot项目开发中是常用的缓存套件,常见使用的是spring-boot-starter-data-redisspringboot 查看详情

logstash2.3.4趟坑之集成redis哨兵模式

最新在使用Lostash2.3.4收集数据的时候,在读取redis数据的时候,报了如下的一个异常:异常如下Pipelineabortedduetoerror{:exception=>#<URI::InvalidURIError:theschemeredisdoesnotacceptregistrypart:redis_master_10214(orbadhostname?)>,: 查看详情

springboot2.x整合redis以及连接哨兵模式/集群模式

依赖:<!--spirngboot版本为2.x--><!--加载springbootredis包,springboot2.0中直接使用jedis或者lettuce配置连接池,默认为lettuce连接池,这里使用jedis连接池--><!--加载springbootredis包--><dependency> <groupId>org.spr 查看详情

springboot入门教程-redis发布订阅模式(代码片段)

一:Redis发布订阅Redis可以像MQ一样发布消息和订阅消息,只不过这种发布订阅是广播模式,即每个订阅者都会收到相同的消息。二:集成pom.xml<dependency><groupId>org.springframework.boot</groupId><artifactId>spring-boot-starter-we... 查看详情

redis主从复制哨兵集群模式(代码片段)

Redis主从复制、哨兵、集群模式单节点模式SpringBoot整合@Bean(name="singleClient")publicRedissonClientsingleRedissonClient()tryConfigconfig=newConfig();config.useSingleServer().setAddress("redis://& 查看详情

redis哨兵模式搭建(一主二从三哨兵)

...有一直报读取错误,无法切换到其它服务节点,请尝试将springboot版本升级到2.3.0,或者将redis的startjar包升级到更高版本 查看详情

springboot学习springboot集成shiro前后端分离使用redis做缓存个人博客搭建(代码片段)

shiro-redis目录shiro-redis下载shiro-core/jedis版本对比图使用前如何配置?设置文件Redis独立Redis哨兵Redis集群SpringRedis独立Redis哨兵Redis集群序列化器Serializer可配置选项ConfigurableOptionsRedis管理器RedisSessionDAOCacheManager缓存管理器弹簧启... 查看详情

三分钟带你入门redis高可用架构之哨兵模式,文末有彩蛋

一般来说,零基础从入门到就业,所学学习内容如下,今天划重点的内容是第一个文件夹:001基础(se)二、其中第一个文件夹,001基础(se)作为整个java的语法思想等基础,下面我来进行... 查看详情

redis学习总结(3)redis哨兵模式

...用的一种选择。本文先介绍下哨兵模式,再介绍了如何在springboot项目中使用。这意味着使用Sentinel(哨兵模式),您可以创建一个Redis部署,它可抵抗某些类型的故障(进行故障迁移)而无需人工干预。它有这些功能:Sentinel的... 查看详情

重学springboot系列之redis与springcache缓存(代码片段)

重学SpringBoot系列之redis缓存使用docker安装redis准备工作获取redis镜像创建容器创建持久化存储目录获取redis的默认配置文件模版使用镜像创建一个容器查看活跃的容器访问redis容器服务开启防火墙端口,提供外部访问redis数据结... 查看详情

springboot+sentinel+redisson集成

参考技术A由于项目中需要使用springboot、redis、redisson,现将自己的配置记录下。spring-boot-starter-parent2.3.4.RELEASEspring-boot-starter-web2.3.4.RELEASEspring-boot-starter-data-redis2.3.4.RELEASEredisson-spring-boot-starter3.17.3pom.xml文件如下:配置文件有两种... 查看详情

springboot集成redisson(单机,集群,哨兵)

1.springBoot集成redisson(单机,集群,哨兵)redisson版本使用3.8.2<dependency>??????<groupId>org.redisson</groupId>??????<artifactId>redisson</artifactId>??????<version>3.8.2</ve 查看详情

springboot-集成redis

这里主要讲述SpringBoot集成Redis的使用,因此不再详述Redis,如果需要请自行百度博主也有写过Redis文章,如下Redis入门简介Redis(RemoteDictionaryServer)译为“远程字典服务”Redis是一个用C语言编写的、开源的、基... 查看详情

redis哨兵模式

redis_sentinel哨兵模式;Redis架构一般多是一主多从;sentinel三组进行相互监控;wgethttp://download.redis.io/releases/redis-3.2.4.tar.gztar-zxvfredis-3.2.4.tar.gzcdredismake&&makeinstallcp-rpredis/src/redis-trib.rb/usr/l 查看详情

redis(二十八)-redis的哨兵模式(代码片段)

...网打尽,9.9元买不了吃亏,买不了上当。Python从入门到精通❤️2.Python爬虫专栏,系统性的学习爬虫的知识点。9.9元买不了吃亏,买不了上当。python 查看详情