前两篇我们讲了Guava和JetCache,他们都是缓存的具体实现,今天给大家分析一下Spring框架本身对这些缓存具体实现的支持和融合,使用Spring Cache将大大的减少我们的Spring项目中缓存使用的复杂度,提高代码可读性。本文将从以下几个方面来认识Spring Cache框架
背景
SpringCache产生的背景其实与Spring产生的背景有点类似。由于Java EE 系统框架臃肿、低效,代码可观性低,对象创建和依赖关系复杂,Spring框架出来了,目前基本上所有的Java后台项目都离不开Spring或SpringBoot(对Spring的进一步简化)。现在项目面临高并发的问题越来越多,各类缓存的应用也增多,那么在通用的Spring框架上,就需要有一种更加便捷简单的方式,来完成缓存的支持,就这样SpringCache就出现了。
不过首先我们需要明白的一点是,SpringCache并非某一种Cache实现的技术,SpringCache是一种缓存实现的通用技术,基于Spring提供的Cache框架,让开发者更容易将自己的缓存实现高效便捷的嵌入到自己的项目中。当然,SpringCache也提供了本身的简单实现NoOpCacheManager、ConcurrentMapCacheManager 等。通过SpringCache,可以快速嵌入自己的Cache实现。
用法
源码已分享至github:https://github.com/zhuzhenke/common-caches
注意点:
1、开启EnableCaching注解,默认是没有开启Cache的
2、配置CacheManager
@Bean
@Qualifier("concurrentMapCacheManager")
@Primary
ConcurrentMapCacheManager concurrentMapCacheManager() {
return new ConcurrentMapCacheManager();
}
这里使用了@Primary和@Qualifier注解,@Qualifier注解是给这个bean加一个名字,用于同一个接口bean的多个实现时,指定当前bean的名字,也就意味着CacheManager可以配置多个,并且在不同的方法场景下使用。@Primary注解是当接口bean有多个时,优先注入当前bean。
现在拿CategoryService实现来分析
public class CategoryService {
@Caching(evict = {@CacheEvict(value = CategoryCacheConstants.CATEGORY_DOMAIN,
key = "#category.getCategoryCacheKey()",
beforeInvocation = true)})
public int add(Category category) {
System.out.println("模拟进行数据库交互操作......");
System.out.println("Cache became invalid,value:" + CategoryCacheConstants.CATEGORY_DOMAIN
+ ",key:" + category.getCategoryCacheKey());
return 1;
}
@Caching(evict = {@CacheEvict(value = CategoryCacheConstants.CATEGORY_DOMAIN,
key = "#category.getCategoryCacheKey()",
beforeInvocation = true)})
public int delete(Category category) {
System.out.println("模拟进行数据库交互操作......");
System.out.println("Cache became invalid,value:" + CategoryCacheConstants.CATEGORY_DOMAIN
+ ",key:" + category.getCategoryCacheKey());
return 0;
}
@Caching(evict = {@CacheEvict(value = CategoryCacheConstants.CATEGORY_DOMAIN,
key = "#category.getCategoryCacheKey()")})
public int update(Category category) {
System.out.println("模拟进行数据库交互操作......");
System.out.println("Cache updated,value:" + CategoryCacheConstants.CATEGORY_DOMAIN
+ ",key:" + category.getCategoryCacheKey()