2019独角兽企业重金招聘Python工程师标准>>> hot3.png

请先看

https://my.oschina.net/u/3866531/blog/1840386

CompositeCacheManager

Composite,混合的,混成的

Spring提供CompositeCacheManager的主要目的就是为了混合使用多种缓存时进行管理。

一、实际测试--CompositeCacheManager中打断点

断点打在getCache上

GuavaDataCache源码--去掉类上的@CacheConfig(cacheManager = "guavaCacheManager")注解

package com.ding.data.cache;import java.text.SimpleDateFormat;import java.util.Date;import java.util.HashMap;import java.util.Map;import javax.annotation.PostConstruct;import org.springframework.cache.annotation.CacheEvict;import org.springframework.cache.annotation.CachePut;import org.springframework.cache.annotation.Cacheable;import org.springframework.stereotype.Service;@Service//@CacheConfig(cacheManager = "guavaCacheManager")public class GuavaDataCache {private Map<Long, String> dataMap = new HashMap<Long, String>();/*** 初始化*/@PostConstructpublic void init() {dataMap.put(1L, "张三");dataMap.put(2L, "李四");dataMap.put(3L, "王五");}/*** 查询* 如果数据没有缓存,那么从dataMap里面获取,如果缓存了,* 那么从guavaDemo里面获取* 并且将缓存的数据存入到 guavaDemo里面* 其中key 为 #id+dataMap*/@Cacheable(value="guavaDemo" ,key="#id + 'dataMap'")public String query(Long id) {SimpleDateFormat sdf = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss");System.out.println(sdf.format(new Date()) + " : query id is " + id);return dataMap.get(id);}/*** 插入 或者更新* 插入或更新数据到dataMap中* 并且缓存到 guavaDemo中* 如果存在了那么更新缓存中的值* 其中key 为 #id+dataMap*/@CachePut(value="guavaDemo" ,key="#id + 'dataMap'")public String put(Long id, String value) {SimpleDateFormat sdf = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss");System.out.println(sdf.format(new Date()) + " : add data ,id is "+ id);dataMap.put(id, value);// data persistencereturn value;}/*** 删除* 删除dataMap里面的数据* 并且删除缓存guavaDemo中的数据* 其中key 为 #id+dataMap*/@CacheEvict(value="guavaDemo" , key="#id + 'dataMap'")public void remove(Long id) {SimpleDateFormat sdf = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss");System.out.println(sdf.format(new Date()) + " : remove id is "+ id + " data");dataMap.remove(id);// data remove  }}

RedisDataCache源码--去掉类上的@CacheConfig(cacheManager = "redisCacheManager")注解

package com.ding.data.cache;import java.text.SimpleDateFormat;import java.util.Date;import java.util.HashMap;import java.util.Map;import javax.annotation.PostConstruct;import org.springframework.cache.annotation.CacheEvict;import org.springframework.cache.annotation.CachePut;import org.springframework.cache.annotation.Cacheable;import org.springframework.stereotype.Service;@Service//@CacheConfig(cacheManager = "redisCacheManager")public class RedisDataCache {private Map<Long, String> dataMap = new HashMap<Long, String>();/*** 初始化*/@PostConstructpublic void init() {dataMap.put(1L, "111");dataMap.put(2L, "222");dataMap.put(3L, "333");}/*** 查询* 如果数据没有缓存,那么从dataMap里面获取,如果缓存了,* 那么从guavaDemo里面获取* 并且将缓存的数据存入到 guavaDemo里面* 其中key 为 #id+dataMap*/@Cacheable(value="redisDemo" ,key="#id + 'dataMap'")public String query(Long id) {SimpleDateFormat sdf = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss");System.out.println(sdf.format(new Date()) + " : query id is " + id);return dataMap.get(id);}/*** 插入 或者更新* 插入或更新数据到dataMap中* 并且缓存到 guavaDemo中* 如果存在了那么更新缓存中的值* 其中key 为 #id+dataMap*/@CachePut(value="redisDemo" ,key="#id + 'dataMap'")public String put(Long id, String value) {SimpleDateFormat sdf = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss");System.out.println(sdf.format(new Date()) + " : add data ,id is "+ id);dataMap.put(id, value);// data persistencereturn value;}/*** 删除* 删除dataMap里面的数据* 并且删除缓存guavaDemo中的数据* 其中key 为 #id+dataMap*/@CacheEvict(value="redisDemo" , key="#id + 'dataMap'")public void remove(Long id) {SimpleDateFormat sdf = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss");System.out.println(sdf.format(new Date()) + " : remove id is "+ id + " data");dataMap.remove(id);// data remove  }}

访问http://localhost:8080/get?id=1,进入断点,看到如下

访问http://localhost:8080/getr?id=1,进入断点,看到如下

所以可见此时是通过CompositeCacheManager进行管理的,CacheConfig类中的CompositeCacheManager 起作用了

package com.ding.data.config;import java.util.ArrayList;import java.util.Arrays;import java.util.List;import java.util.concurrent.TimeUnit;import javax.annotation.Resource;import org.springframework.boot.ApplicationArguments;import org.springframework.boot.ApplicationRunner;import org.springframework.cache.CacheManager;import org.springframework.cache.guava.GuavaCacheManager;import org.springframework.cache.support.CompositeCacheManager;import org.springframework.context.annotation.Bean;import org.springframework.context.annotation.Configuration;import org.springframework.context.annotation.Primary;import org.springframework.data.redis.cache.RedisCacheManager;import org.springframework.data.redis.core.RedisTemplate;import org.springframework.data.redis.serializer.StringRedisSerializer;import com.google.common.cache.CacheBuilder;import com.google.common.collect.Lists;@Configurationpublic class CacheConfig implements ApplicationRunner {@Resourceprivate List<CacheManager> cacheManagers;public void run(ApplicationArguments args) throws Exception {System.out.println("CacheManager大小为=========" + cacheManagers.size());System.out.println("=================================================");for(CacheManager c:cacheManagers){System.out.println(c.getCacheNames());}}@Bean(name = "redisCacheManager")public RedisCacheManager redisCacheManager(RedisTemplate<Object, Object> redisTemplate) {redisTemplate.setKeySerializer(new StringRedisSerializer());RedisCacheManager redisCacheManager = new RedisCacheManager(redisTemplate);redisCacheManager.setCacheNames(Arrays.asList("redisDemo"));redisCacheManager.setUsePrefix(true);return redisCacheManager;}@Bean(name = "guavaCacheManager")public GuavaCacheManager getGuavaCacheManager() {GuavaCacheManager guavaCacheManager = new GuavaCacheManager();guavaCacheManager.setCacheBuilder(CacheBuilder.newBuilder().expireAfterWrite(3600, TimeUnit.SECONDS).maximumSize(1000));ArrayList<String> guavaCacheNames = Lists.newArrayList();guavaCacheNames.add("guavaDemo");guavaCacheManager.setCacheNames(guavaCacheNames);return guavaCacheManager;}@Bean(name = "cacheManager")@Primarypublic CompositeCacheManager cacheManager(RedisCacheManager redisCacheManager,GuavaCacheManager guavaCacheManager) {CompositeCacheManager cacheManager = new CompositeCacheManager(redisCacheManager, guavaCacheManager);return cacheManager;}}
  • 二、实际测试--CompositeCacheManager中打断点

断点打在getCache上

GuavaDataCache源码--加上类上的@CacheConfig(cacheManager = "guavaCacheManager")注解

package com.ding.data.cache;import java.text.SimpleDateFormat;import java.util.Date;import java.util.HashMap;import java.util.Map;import javax.annotation.PostConstruct;import org.springframework.cache.annotation.CacheEvict;import org.springframework.cache.annotation.CachePut;import org.springframework.cache.annotation.Cacheable;import org.springframework.stereotype.Service;@Service@CacheConfig(cacheManager = "guavaCacheManager")public class GuavaDataCache {private Map<Long, String> dataMap = new HashMap<Long, String>();/*** 初始化*/@PostConstructpublic void init() {dataMap.put(1L, "张三");dataMap.put(2L, "李四");dataMap.put(3L, "王五");}/*** 查询* 如果数据没有缓存,那么从dataMap里面获取,如果缓存了,* 那么从guavaDemo里面获取* 并且将缓存的数据存入到 guavaDemo里面* 其中key 为 #id+dataMap*/@Cacheable(value="guavaDemo" ,key="#id + 'dataMap'")public String query(Long id) {SimpleDateFormat sdf = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss");System.out.println(sdf.format(new Date()) + " : query id is " + id);return dataMap.get(id);}/*** 插入 或者更新* 插入或更新数据到dataMap中* 并且缓存到 guavaDemo中* 如果存在了那么更新缓存中的值* 其中key 为 #id+dataMap*/@CachePut(value="guavaDemo" ,key="#id + 'dataMap'")public String put(Long id, String value) {SimpleDateFormat sdf = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss");System.out.println(sdf.format(new Date()) + " : add data ,id is "+ id);dataMap.put(id, value);// data persistencereturn value;}/*** 删除* 删除dataMap里面的数据* 并且删除缓存guavaDemo中的数据* 其中key 为 #id+dataMap*/@CacheEvict(value="guavaDemo" , key="#id + 'dataMap'")public void remove(Long id) {SimpleDateFormat sdf = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss");System.out.println(sdf.format(new Date()) + " : remove id is "+ id + " data");dataMap.remove(id);// data remove  }}

RedisDataCache源码--去掉类上的@CacheConfig(cacheManager = "redisCacheManager")注解

package com.ding.data.cache;import java.text.SimpleDateFormat;import java.util.Date;import java.util.HashMap;import java.util.Map;import javax.annotation.PostConstruct;import org.springframework.cache.annotation.CacheEvict;import org.springframework.cache.annotation.CachePut;import org.springframework.cache.annotation.Cacheable;import org.springframework.stereotype.Service;@Service@CacheConfig(cacheManager = "redisCacheManager")public class RedisDataCache {private Map<Long, String> dataMap = new HashMap<Long, String>();/*** 初始化*/@PostConstructpublic void init() {dataMap.put(1L, "111");dataMap.put(2L, "222");dataMap.put(3L, "333");}/*** 查询* 如果数据没有缓存,那么从dataMap里面获取,如果缓存了,* 那么从guavaDemo里面获取* 并且将缓存的数据存入到 guavaDemo里面* 其中key 为 #id+dataMap*/@Cacheable(value="redisDemo" ,key="#id + 'dataMap'")public String query(Long id) {SimpleDateFormat sdf = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss");System.out.println(sdf.format(new Date()) + " : query id is " + id);return dataMap.get(id);}/*** 插入 或者更新* 插入或更新数据到dataMap中* 并且缓存到 guavaDemo中* 如果存在了那么更新缓存中的值* 其中key 为 #id+dataMap*/@CachePut(value="redisDemo" ,key="#id + 'dataMap'")public String put(Long id, String value) {SimpleDateFormat sdf = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss");System.out.println(sdf.format(new Date()) + " : add data ,id is "+ id);dataMap.put(id, value);// data persistencereturn value;}/*** 删除* 删除dataMap里面的数据* 并且删除缓存guavaDemo中的数据* 其中key 为 #id+dataMap*/@CacheEvict(value="redisDemo" , key="#id + 'dataMap'")public void remove(Long id) {SimpleDateFormat sdf = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss");System.out.println(sdf.format(new Date()) + " : remove id is "+ id + " data");dataMap.remove(id);// data remove  }}

访问http://localhost:8080/get?id=1,没进入断点

访问http://localhost:8080/getr?id=1,没进入断点

所以可见,此时因为标注上了 @CacheConfig(cacheManager = "guavaCacheManager") 和 @CacheConfig(cacheManager = "redisCacheManager") ,所以直接就知道需要用哪个CacheManager了,不需要CompositeCacheManager去匹配了

直接去掉CacheConfig类中的CompositeCacheManager ,在不同的缓存上加上 @CacheConfig(cacheManager = "guavaCacheManager") 和 @CacheConfig(cacheManager = "redisCacheManager"),是否可以?——测试一下

此时的CacheConfig类代码

package com.ding.data.config;import java.util.ArrayList;import java.util.Arrays;import java.util.List;import java.util.concurrent.TimeUnit;import javax.annotation.Resource;import org.springframework.boot.ApplicationArguments;import org.springframework.boot.ApplicationRunner;import org.springframework.cache.CacheManager;import org.springframework.cache.guava.GuavaCacheManager;import org.springframework.context.annotation.Bean;import org.springframework.context.annotation.Configuration;import org.springframework.data.redis.cache.RedisCacheManager;import org.springframework.data.redis.core.RedisTemplate;import org.springframework.data.redis.serializer.StringRedisSerializer;import com.google.common.cache.CacheBuilder;import com.google.common.collect.Lists;@Configurationpublic class CacheConfig implements ApplicationRunner {@Resourceprivate List<CacheManager> cacheManagers;public void run(ApplicationArguments args) throws Exception {System.out.println("CacheManager大小为=========" + cacheManagers.size());System.out.println("=================================================");for(CacheManager c:cacheManagers){System.out.println(c.getCacheNames());}}@Bean(name = "redisCacheManager")public RedisCacheManager redisCacheManager(RedisTemplate<Object, Object> redisTemplate) {redisTemplate.setKeySerializer(new StringRedisSerializer());RedisCacheManager redisCacheManager = new RedisCacheManager(redisTemplate);redisCacheManager.setCacheNames(Arrays.asList("redisDemo"));redisCacheManager.setUsePrefix(true);return redisCacheManager;}@Bean(name = "guavaCacheManager")public GuavaCacheManager getGuavaCacheManager() {GuavaCacheManager guavaCacheManager = new GuavaCacheManager();guavaCacheManager.setCacheBuilder(CacheBuilder.newBuilder().expireAfterWrite(3600, TimeUnit.SECONDS).maximumSize(1000));ArrayList<String> guavaCacheNames = Lists.newArrayList();guavaCacheNames.add("guavaDemo");guavaCacheManager.setCacheNames(guavaCacheNames);return guavaCacheManager;}// @Bean(name = "cacheManager")// @Primary// public CompositeCacheManager cacheManager(// RedisCacheManager redisCacheManager,// GuavaCacheManager guavaCacheManager) {// CompositeCacheManager cacheManager = new CompositeCacheManager(// redisCacheManager, guavaCacheManager);// return cacheManager;// }}

结果启动时就报错了

java.lang.IllegalStateException: No CacheResolver specified, and no unique bean of type CacheManager found. Mark one as primary (or give it the name 'cacheManager') or declare a specific CacheManager to use, that serves as the default one.

at org.springframework.cache.interceptor.CacheAspectSupport.afterSingletonsInstantiated(CacheAspectSupport.java:186) ~[spring-context-4.2.6.RELEASE.jar:4.2.6.RELEASE]

at org.springframework.beans.factory.support.DefaultListableBeanFactory.preInstantiateSingletons(DefaultListableBeanFactory.java:792) ~[spring-beans-4.2.6.RELEASE.jar:4.2.6.RELEASE]

at org.springframework.context.support.AbstractApplicationContext.finishBeanFactoryInitialization(AbstractApplicationContext.java:839) ~[spring-context-4.2.6.RELEASE.jar:4.2.6.RELEASE]

at org.springframework.context.support.AbstractApplicationContext.refresh(AbstractApplicationContext.java:538) ~[spring-context-4.2.6.RELEASE.jar:4.2.6.RELEASE]

at org.springframework.boot.context.embedded.EmbeddedWebApplicationContext.refresh(EmbeddedWebApplicationContext.java:118) ~[spring-boot-1.3.5.RELEASE.jar:1.3.5.RELEASE]

at org.springframework.boot.SpringApplication.refresh(SpringApplication.java:766) [spring-boot-1.3.5.RELEASE.jar:1.3.5.RELEASE]

at org.springframework.boot.SpringApplication.createAndRefreshContext(SpringApplication.java:361) [spring-boot-1.3.5.RELEASE.jar:1.3.5.RELEASE]

at org.springframework.boot.SpringApplication.run(SpringApplication.java:307) [spring-boot-1.3.5.RELEASE.jar:1.3.5.RELEASE]

at org.springframework.boot.SpringApplication.run(SpringApplication.java:1191) [spring-boot-1.3.5.RELEASE.jar:1.3.5.RELEASE]

at org.springframework.boot.SpringApplication.run(SpringApplication.java:1180) [spring-boot-1.3.5.RELEASE.jar:1.3.5.RELEASE]

at com.ding.data.App.main(App.java:33) [classes/:na]

上面报错是因为Spring Context 中存在多个实现了 CacheManager.class 的 Bean,需要使用 @Primary 注解指定优先选择的 CacheManager

那么指定 GuavaCacheManager 为 @Primary,此时的CacheConfig类代码

package com.ding.data.config;import java.util.ArrayList;import java.util.Arrays;import java.util.List;import java.util.concurrent.TimeUnit;import javax.annotation.Resource;import org.springframework.boot.ApplicationArguments;import org.springframework.boot.ApplicationRunner;import org.springframework.cache.CacheManager;import org.springframework.cache.guava.GuavaCacheManager;import org.springframework.context.annotation.Bean;import org.springframework.context.annotation.Configuration;import org.springframework.context.annotation.Primary;import org.springframework.data.redis.cache.RedisCacheManager;import org.springframework.data.redis.core.RedisTemplate;import org.springframework.data.redis.serializer.StringRedisSerializer;import com.google.common.cache.CacheBuilder;import com.google.common.collect.Lists;@Configurationpublic class CacheConfig implements ApplicationRunner {@Resourceprivate List<CacheManager> cacheManagers;public void run(ApplicationArguments args) throws Exception {System.out.println("CacheManager大小为=========" + cacheManagers.size());System.out.println("=================================================");for(CacheManager c:cacheManagers){System.out.println(c.getCacheNames());}}@Bean(name = "redisCacheManager")public RedisCacheManager redisCacheManager(RedisTemplate<Object, Object> redisTemplate) {redisTemplate.setKeySerializer(new StringRedisSerializer());RedisCacheManager redisCacheManager = new RedisCacheManager(redisTemplate);redisCacheManager.setCacheNames(Arrays.asList("redisDemo"));redisCacheManager.setUsePrefix(true);return redisCacheManager;}@Bean(name = "guavaCacheManager")@Primarypublic GuavaCacheManager getGuavaCacheManager() {GuavaCacheManager guavaCacheManager = new GuavaCacheManager();guavaCacheManager.setCacheBuilder(CacheBuilder.newBuilder().expireAfterWrite(3600, TimeUnit.SECONDS).maximumSize(1000));ArrayList<String> guavaCacheNames = Lists.newArrayList();guavaCacheNames.add("guavaDemo");guavaCacheManager.setCacheNames(guavaCacheNames);return guavaCacheManager;}// @Bean(name = "cacheManager")// @Primary// public CompositeCacheManager cacheManager(// RedisCacheManager redisCacheManager,// GuavaCacheManager guavaCacheManager) {// CompositeCacheManager cacheManager = new CompositeCacheManager(// redisCacheManager, guavaCacheManager);// return cacheManager;// }}

正常启动,刚才的报错消失

测试,一切正常

所以不需要使用CompositeCacheManager类,在使用缓存的地方通过 @CacheConfig 指定CacheManager,就可以混合使用多种缓存组件了。同时,要记得在配置类中指定一个 @Primary 缓存

转载于:https://my.oschina.net/u/3866531/blog/1840530

SpringBoot同时集成Redis和Guava作为缓存组件--进一步分析代码相关推荐

  1. SpringBoot 05 集成redis实现对象序列化缓存

    1.为什么用Spring Data Spring Data 的目标是为数据访问提供一个基于Spring的普遍常用的编程模型,同时仍然保留底层数据存储的特殊特性, 它让使用数据访问技术.关系和非关系数据 ...

  2. 【JAVA秘籍功法篇-SpringBoot】SpringBoot如何集成Redis?

    SpringBoot如何集成redis 大家好,我是王老狮,一个有思想有内涵的架构狮.Redis作为分布式缓存,在我们的项目中经常会用到,今天我们看下SpringBoot如何集成redis. POM中 ...

  3. Springboot:整合redis对接口数据进行缓存

    文章目录 Springboot:整合redis对接口数据进行缓存 一.注解及其属性介绍 @Cacheable @CacheEvict @CachePut @CacheConfig 二.代码实现 1.创 ...

  4. SpringBoot中集成Redis实现对redis中数据的解析和存储

    场景 SpringBoot中操作spring redis的工具类: SpringBoot中操作spring redis的工具类_霸道流氓气质的博客-CSDN博客 上面讲的操作redis的工具类,但是对 ...

  5. SpringBoot2.0 基础案例(08):集成Redis数据库,实现缓存管理

    一.Redis简介 Spring Boot中除了对常用的关系型数据库提供了优秀的自动化支持之外,对于很多NoSQL数据库一样提供了自动化配置的支持,包括:Redis, MongoDB, Elastic ...

  6. go语言高性能缓存组件ccache分析

    1. 背景 在撸代码时,利用局部性原理对数据做缓存是一种常用的性能优化手段. 要做缓存,离不开的就是缓存组件.ccache就是一个很优秀的lru缓存组件,其做了很多很巧妙的优化策略来降低锁冲突,实现高 ...

  7. SpringBoot简单集成Redis,实现简单查询

    1引入redis的依赖 <dependency><groupId>org.springframework.boot</groupId><artifactId& ...

  8. Redis第三话 – Springboot集成Redis以及常用API和客户端介绍

    本文主要记录在Springboot中集成Redis的使用. 1. springboot集成redis 1.1 maven配置 基于springboot 版本2.5.6,parent包就不贴了. < ...

  9. spring boot 缓存_Spring Boot 集成 Redis 实现数据缓存

    Spring Boot 集成 Redis 实现数据缓存,只要添加一些注解方法,就可以动态的去操作缓存了,减少代码的操作. 在这个例子中我使用的是 Redis,其实缓存类型还有很多,例如 Ecache. ...

最新文章

  1. python3最新版本-Python3第三方组件最新版本追踪实现
  2. KVM中virtio、vhost 和vhost-user比较(十一)
  3. java、intellij idea、groovy
  4. 实例3:按部门统计工资人数
  5. 【渝粤题库】陕西师范大学202881 电子商务概论
  6. 深度残差网络的无人机多目标识别
  7. java规定日期格式输出_Java格式化输出日期百分比时间等
  8. 事件Event:带你体验鸿蒙轻内核中一对多、多对多任务同步
  9. 一加、OPPO官宣合并,“父子团圆”能否拯救一加?
  10. 软件著作权算法软件设计说明书_软件详细设计说明书例子.pdf
  11. Grouping BP has not been assigned to any customer accounts groupMessage no. FSBP_ECC004
  12. 【数学模拟卷总结】2022李林四套卷数学二第二套
  13. 在 HTML 中使用 ARIA 的规则
  14. shell foreach
  15. php 图片获得大小,PHP获取一张图片的宽度和高度大小 并裁切图片
  16. html app下载页功能开发
  17. selenium找到页面元素click没反应
  18. 关于Windows在ping虚拟机时出现请求超时的解决问题
  19. 海康嵌入式软件面试经验(已拿offer)
  20. The CompactFlash Association宣布推出CFexpress(R)2.0规范

热门文章

  1. Android开发工具新接触
  2. 重置密码遇到ERROR 1045 (28000): Access denied for user ‘root‘@‘localhost‘ (using passwor:yes)问题
  3. python 字符串反转
  4. 基于python的移动物体检测_感兴趣区域的移动物体检测,框出移动物体的轮廓 (固定摄像头, opencv-python)...
  5. 剑指offer java 博客_Java--剑指offer(10)
  6. access设计视图打不开_定制橱柜衣柜怎么测量才能避免出错?(设计师必看)
  7. 微信小程序长按保存图片
  8. linux shell 学习小结
  9. mysql+数据库连接标识_新人必看!连接到MySQL数据库的两种方法
  10. 顺序表应用3:元素位置互换之移位算法