1.引入依赖
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-cache</artifactId>
</dependency>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-data-redis</artifactId>
</dependency>
Application启动类上
开启缓存 @EnableCaching
2.写配置
(1)自动配置,CacheAutoConfiguration.class
CacheConfigurationImportSelector 方法又导入很多缓存配置组件
CacheProperties.class
自动配置了RedisCacheManager缓存管理器
(2).我们自己要配置,redis的配置和下面的缓存配置
spring.cache.type=redis
3.测试使用缓存
@Cacheable:触发将数据保存到缓存
@CacheEvict:触发将数据从缓存删除
@CachePut:不影响方法执行更新缓存
@Caching:组合以上多个操作
@CacheConfig:在类级别上共享缓存的相同配置
@Cacheable(value = {"menuById"}, key = "'id-' + #menu.id")
public Menu findById(Menu menu) {
return menu;
}
#缓存前缀,没有指定就用缓存的名字,menuById
spring.cache.redis.key-prefix=CACHE_
#没有值使用缓存null值,防止缓存穿透
spring.cache.redis.cache-null-values=true
缓存配置细节:
默认缓存自动生成的键,用jdk序列化,ttl=-1永不过期
自定义:
1.key :@Cacheable(value={“menuById”},key="‘id’") 结果为menuById::id
2.存活时间 在配置文件中指定 spring.cache.redis.time-to-live=3600000(1小时)
3.指定格式json
注释:@EnableConfigurationProperties(CacheProperties.class)//原来不在容器中,开启绑定,为我们自己所用
@Autowired
CacheProperties cacheProperties;//拿到上面的CacheProperties,或者直接放在下面的方法传参上,能自动拿到
/**
* 自定义缓存的配置
*/
@EnableConfigurationProperties(CacheProperties.class)//原来不在容器中,开启绑定,为我们自己所用
@EnableCaching
@Configuration
public class CacheConfig {
@Autowired
CacheProperties cacheProperties;//拿到上面的CacheProperties,或者直接放在下面的方法传参上,能自动拿到
@Bean
public RedisCacheConfiguration redisCacheConfiguration(CacheProperties cacheProperties){
RedisCacheConfiguration config = RedisCacheConfiguration.defaultCacheConfig();
config = config.serializeKeysWith(RedisSerializationContext.SerializationPair.fromSerializer(new StringRedisSerializer()));
config = config.serializeValuesWith(RedisSerializationContext.SerializationPair.fromSerializer(new GenericJackson2JsonRedisSerializer()));
CacheProperties.Redis redisProperties = cacheProperties.getRedis();
if (redisProperties.getTimeToLive() != null) {
config = config.entryTtl(redisProperties.getTimeToLive());
}
if (redisProperties.getKeyPrefix() != null) {
config = config.prefixCacheNameWith(redisProperties.getKeyPrefix());
}
if (!redisProperties.isCacheNullValues()) {
config = config.disableCachingNullValues();
}
if (!redisProperties.isUseKeyPrefix()) {
config = config.disableKeyPrefix();
}
return config;
}
}
4.spring-cache 的原理与不足
原理:CacheManager(RedisCacheManager) ->Cache(RedisCache)->Cache
不足:
(1)读模式:
缓存击穿,spring.cache.redis.cache-null-values=true 解决、
缓存穿透,解决:加锁,默认不加,sync=true 加锁(本地锁足够)
缓存雪崩,加上过期时间 spring.cache.redis.time-to-live=3600000
(2)写模式:springcache没有管
总结:读多写少数据完全可以使用spring cache