本文介绍如何为Spring Boot应用添加缓存。
缓存就是数据交换的缓冲区,用来提高存取数据的速度。将经常访问又不经常改变的数据存入缓存,可以提高系统性能和吞吐量。通过设置一二级缓存:将系统内存作为一级缓存,存储热点数据;将缓存服务器作为二级缓存,存储常用数据。不仅可以保证热点数据获取的效率,还可以避免缓存占用系统过多内存。
SpringBoot提供了spring-boot-starter-cache
为多种缓存实现提供了简单且统一的使用方式。
<dependency>
<groupId>org.springframework.bootgroupId>
<artifactId>spring-boot-starter-cacheartifactId>
dependency>
@Cacheable("user")
public User findById(Integer id){
// 略
}
@EnableCaching
@SpringBootApplication
public class CacheApplication {
public static void main(String[] args) {
SpringApplication.run(CacheApplication.class, args);
}
}
SpringBoot提供的缓存注解有下面几种
若缓存存在,则跳过方法执行,直接返回缓存结果。
若缓存不存在,则执行方法,并将结果缓存。
将方法执行结果存入指定缓存
当方法执行后清除指定缓存
若一个方法执行需要对缓存进行多个操作,通过该注解实现。
@Caching(
cacheable = {@Cacheable("cache1"), @Cacheable("cache2")},
evict = {@CacheEvict("cache1"), @CacheEvict("cache2")},
put = {@CachePut("cache1"), @CachePut("cache2")}
)
public void testMethod(){
// 略
}
标记在类上,为整个类的缓存注解提供相同的配置,如:cacheNames、keyGenerator等。
使用如下
@Cacheable(cacheNames="user",key="#id")
public User findById(Long id){
// 略
}
SpringBoot提供了SimpleKeyGenerator
作为默认的key生成器。下面介绍如何定制并使用key生成器。
public class CustomKeyGenerator implements KeyGenerator {
@Override
public Object generate(Object target, Method method, Object... params){
return Objects.hash(params);
}
}
@Configuration
public class Config {
@Bean
public KeyGenerator customKeyGenerator() {
return new CustomKeyGenerator();
}
}
@Cacheable(cacheNames="user",keyGenerator="customKeyGenerator")
public User findById(Long id){
// 略
}
// 方法参数作为条件
@Cacheable(cacheNames="user",condition="#id>0")
public User findById(Long id){
// 略
}
// 方法执行结果作为条件
@Cacheable(cacheNames="user",unless="#result!=0")
public User findById(Long id){
// 略
}
通过注解控制缓存是由JSR107规范提出的,但是其提供的注解并不好用,https://github.com/jsr107/jsr107spec/issues/86,可以看看这里。
Spring缓存是通过AOP创建代理类拦截方法实现的缓存,直接调用本类方法无法触发缓存的拦截,可以通过下面的方法触发缓存。
public class CacheServiceImpl implements CacheService{
@Autowired
private CacheService instance;
@Cacheable
public void m1(){
instance.m2();
}
@Cacheable
public void m2(){
instance.m1();
}
}