欢迎您访问365答案网,请分享给你的朋友!
生活常识 学习资料

SpringBoot缓存之@Cacheable介绍

时间:2023-08-10

目录

1 概述

2 @Cacheable注解使用详细介绍

        2.1 @Cacheable注解使用

        2.2  Cacheable 注解的属性


1 概述

        Spring高版本引入了cache的注解技术。该技术是一种规范。Redis的cache技术,底层使用的是Spring Data Redis。cache技术的使用需要掌握的有@EnableCaching、@Cacheable、@CacheEvict、@Caching、@CacheConfig注解的使用,这些注解支持SpringSPEL表达式方式。

今天先了解@Cacheable注解。

2 @Cacheable注解使用详细介绍

        2.1 @Cacheable注解使用

步骤一:cacheConfig配置类

package com.liubujun.redis_springboot.config;import com.fasterxml.jackson.annotation.JsonAutoDetect;import com.fasterxml.jackson.annotation.PropertyAccessor;import com.fasterxml.jackson.databind.ObjectMapper;import org.springframework.cache.CacheManager;import org.springframework.cache.annotation.EnableCaching;import org.springframework.context.annotation.Bean;import org.springframework.context.annotation.Configuration;import org.springframework.data.redis.cache.RedisCacheConfiguration;import org.springframework.data.redis.cache.RedisCacheManager;import org.springframework.data.redis.connection.RedisConnectionFactory;import org.springframework.data.redis.serializer.Jackson2JsonRedisSerializer;import org.springframework.data.redis.serializer.RedisSerializationContext;import org.springframework.data.redis.serializer.StringRedisSerializer;import java.time.Duration;import java.util.HashMap;import java.util.Map;@Configuration@EnableCachingpublic class CacheConfig { @Bean public CacheManager cacheManager(RedisConnectionFactory redisConnectionFactory){ RedisCacheManager redisCacheManager = RedisCacheManager.builder(redisConnectionFactory) .cacheDefaults(defaultCacheConfig(10000)) .withInitialCacheConfigurations(initCacheConfigMap()) .transactionAware() .build(); return redisCacheManager; } private RedisCacheConfiguration defaultCacheConfig(Integer second) { Jackson2JsonRedisSerializer jackson2JsonRedisSerializer = new Jackson2JsonRedisSerializer(Object.class); //解决查询缓存转换异常的问题 ObjectMapper om = new ObjectMapper(); om.setVisibility(PropertyAccessor.ALL, JsonAutoDetect.Visibility.ANY); om.enableDefaultTyping(ObjectMapper.DefaultTyping.NON_FINAL); jackson2JsonRedisSerializer.setObjectMapper(om); //配置序列化 解决乱码的问题 RedisCacheConfiguration config = RedisCacheConfiguration.defaultCacheConfig() .entryTtl(Duration.ofSeconds(second)) .serializeKeysWith(RedisSerializationContext.SerializationPair.fromSerializer(new StringRedisSerializer())) .serializevaluesWith(RedisSerializationContext.SerializationPair.fromSerializer(jackson2JsonRedisSerializer)) .disableCachingNullValues(); return config; } private Map initCacheConfigMap() { Map configMap = new HashMap<>(); configMap.put("User",this.defaultCacheConfig(1000)); configMap.put("User1",this.defaultCacheConfig(1000)); configMap.put("User2",this.defaultCacheConfig(1000)); configMap.put("User3",this.defaultCacheConfig(1000)); return configMap; }}

步骤二:application.properties文件配置redis的参数

#redis服务器地址(自己redis所在主机地址)spring.redis.host=*******#redis服务器连接端口spring.redis.port=6379#redis数据库索引(默认是0)spring.redis.database=0#连接超时时间spring.redis.timeout=1800000#连接池最大连接数(使用负值表示没有限制)spring.redis.lettuce.pool.max-active=20#最大阻塞等待时间(负数表示没有限制)spring.redis.lettuce.pool.max-wait=-1#连接池中最大空闲连接spring.redis.lettuce.pool.max-idle=5#连接池中最小空闲连接spring.redis.lettuce.pool.min-idle=0

步骤三:测试类编写

package com.liubujun.redis_springboot.controller;import com.liubujun.redis_springboot.entity.User;import org.springframework.cache.annotation.Cacheable;import org.springframework.cache.annotation.EnableCaching;import org.springframework.data.redis.core.RedisTemplate;import org.springframework.web.bind.annotation.GetMapping;import org.springframework.web.bind.annotation.PathVariable;import org.springframework.web.bind.annotation.RequestMapping;import org.springframework.web.bind.annotation.RestController;import javax.annotation.Resource;@RestController@RequestMapping("/redisTest")public class TestController { @GetMapping("/cache/{id}") @Cacheable(cacheNames = "User",key = "#id") //此时缓存中的key为id,value为查询出来的数据(#id就表示取出参数id的值作为key) public User findUserById(@PathVariable("id") Integer id){ User user = new User(); user.setId(id); user.setName("测试:springBooth中Cache"+id+"查询时间戳"+System.currentTimeMillis()); System.out.println("模拟数据库查询数据id:"+id+"name:"+user.getName()); return user; }}

步骤四:浏览器访问

相同id连续两次访问接口

 

控制台只有一句输出语句: 

 

 redis客户端中存储的值:

 

我将用相同的id连续访问两次,控制台只有一句输出语句,那么就说明:第一次访问走了代码逻辑并且将返回结果放入了cacheable中。第二次直接从缓存中取出的数据,没有走代码逻辑。体检了cacheable的作用。

总结: @Cacheable 注解可以将运行结果缓存,以后查询相同的数据,直接从缓存中调取,不需要调用方法,换言之:在方法上加了@Cacheable 注解后,每次调用该方法,都会先检查缓存中有没有相同的key,如果有直接从缓存中获取,没有再调用具体代码逻辑。

        2.2  Cacheable 注解的属性

cacheNames/value :用来指定缓存组件的名字

key :缓存数据时使用的 key,可以用它来指定。默认是使用方法参数的值。(这个 key 你可以使用 spEL 表达式来编写)

keyGenerator :key 的生成器。 key 和 keyGenerator 二选一使用

cacheManager :可以用来指定缓存管理器。从哪个缓存管理器里面获取缓存。

condition :可以用来指定符合条件的情况下才缓存

unless :否定缓存。当 unless 指定的条件为 true ,方法的返回值就不会被缓存。当然你也可以获取到结果进行判断。(通过 #result 获取方法结果)

sync :是否使用异步模式。

1)cacheNames/value :

用来指定缓存组件的名字,将方法的返回结果放在哪个缓存中,可以是数组的方式

@GetMapping("/cache/{id}")@Cacheable(cacheNames = "User") //也可以这样写@Cacheable(cacheNames {"User","Users"})public User findUserByIds(@PathVariable("id") Integer id){ User user = new User(); user.setId(id); user.setName("测试:springBooth中Cache"+id+"查询时间戳"+System.currentTimeMillis()); System.out.println("模拟数据库查询数据id:"+id+"name:"+user.getName()); return user;}

2)key :

缓存数据时使用的key。默认使用的是方法参数的值,也可以使用spEL表达式编写

@GetMapping("/cache/{id}")@Cacheable(cacheNames = "User",key = "#root.methodName+'[' + #id + ']'") //这时如果传入的id为500,那么key=findUserById[500]public User findUserById(@PathVariable("id") Integer id){ User user = new User(); return user;}

3)keyGenerator :

key的生成器,可以用自己指定的生成器去生成key

4)condition :

符合条件的情况下才进行缓存

@GetMapping("/cache/{id}")@Cacheable(cacheNames = "User",condition = "#id >1 ") //这里表示id值大于1时才进行缓存public User findUserByIds(@PathVariable("id") Integer id){ User user = new User(); return user;}

5)unless :

否定缓存,当unless指定的条件为true时,方法的返回值不会被缓存

@GetMapping("/cache/{id}")@Cacheable(cacheNames = "User",unless = "#id >1 ") //这里表示id值大于1时不会进行缓存public User findUserByIds(@PathVariable("id") Integer id){ User user = new User(); return user;}

6)sync :

是否使用异步模式,默认是方法执行完后,以同步的方式将方法返回的结果存在缓存中

参考博客:SpringBoot 缓存之 @Cacheable 详细介绍_勇往直前的专栏-CSDN博客_@cacheable

Copyright © 2016-2020 www.365daan.com All Rights Reserved. 365答案网 版权所有 备案号:

部分内容来自互联网,版权归原作者所有,如有冒犯请联系我们,我们将在三个工作时内妥善处理。