赞
踩
本文操作数据库,使用的是mybatis-plus,关于环境搭建,可查看博文
https://blog.csdn.net/qq_41712271/article/details/115756865
1 添加maven依赖
- <!--redis-->
- <dependency>
- <groupId>org.springframework.boot</groupId>
- <artifactId>spring-boot-starter-data-redis</artifactId>
- </dependency>
- <!--spring cache-->
- <dependency>
- <groupId>org.springframework.boot</groupId>
- <artifactId>spring-boot-starter-cache</artifactId>
- </dependency>
- <!--spring cache连接池依赖包-->
- <dependency>
- <groupId>org.apache.commons</groupId>
- <artifactId>commons-pool2</artifactId>
- <version>2.6.2</version>
- </dependency>
2 配置redis的RedisConfig类
- package cn.jiqistudy.redis_1.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.context.annotation.Bean;
- import org.springframework.context.annotation.Configuration;
- import org.springframework.context.annotation.Primary;
- import org.springframework.data.redis.cache.RedisCacheConfiguration;
- import org.springframework.data.redis.cache.RedisCacheManager;
- import org.springframework.data.redis.cache.RedisCacheWriter;
- import org.springframework.data.redis.connection.RedisConnectionFactory;
- import org.springframework.data.redis.core.RedisTemplate;
- import org.springframework.data.redis.serializer.*;
-
- import java.time.Duration;
-
- /**
- * redisTemplate 序列化使用的jdkSerializeable, 存储二进制字节码, 所以自定义序列化类
- * 开启缓存配置,设置序列化
- */
- @Configuration
- @EnableCaching
- public class RedisConfig {
-
- @Primary
- @Bean
- public CacheManager cacheManager(RedisConnectionFactory redisConnectionFactory){
- RedisCacheConfiguration redisCacheConfiguration = RedisCacheConfiguration.defaultCacheConfig();
- redisCacheConfiguration = redisCacheConfiguration
- //设置缓存的默认超时时间:30分钟
- .entryTtl(Duration.ofMinutes(30L))
- //如果是空值,不缓存
- .disableCachingNullValues()
-
- //设置key序列化器
- .serializeKeysWith(RedisSerializationContext.SerializationPair.fromSerializer(keySerializer()))
- //设置value序列化器
- .serializeValuesWith(RedisSerializationContext.SerializationPair.fromSerializer(valueSerializer()));
-
- return RedisCacheManager
- .builder(RedisCacheWriter.nonLockingRedisCacheWriter(redisConnectionFactory))
- .cacheDefaults(redisCacheConfiguration)
- .build();
- }
-
- /**
- * key序列化器
- */
- private RedisSerializer<String> keySerializer() {
- return new StringRedisSerializer();
- }
- /**
- * value序列化器
- */
- private RedisSerializer<Object> valueSerializer() {
- return new GenericJackson2JsonRedisSerializer();
- }
- }
3 业务处理编写,缓存操作的核心类
- package cn.jiqistudy.redis_1.service;
- import cn.jiqistudy.redis_1.mapper.UserMapper;
- import cn.jiqistudy.redis_1.pojo.User;
- import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
- import org.slf4j.Logger;
- import org.slf4j.LoggerFactory;
- import org.springframework.cache.annotation.CacheConfig;
- import org.springframework.cache.annotation.CacheEvict;
- import org.springframework.cache.annotation.CachePut;
- import org.springframework.cache.annotation.Cacheable;
- import org.springframework.stereotype.Service;
- import javax.annotation.Resource;
-
- @Service
- @CacheConfig(cacheNames = { "user" })
- public class UserService {
-
- private static final Logger LOGGER = LoggerFactory.getLogger(UserService.class);
-
- @Resource
- private UserMapper userMapper;
-
- //新增缓存,注意方法的返回值
- @Cacheable(key="#id")
- public User findUserById(Integer id){
- return this.userMapper.selectById(id);
- }
-
- //更新缓存,注意方法的返回值
- @CachePut(key = "#obj.id")
- public User updateUser(User obj){
- this.userMapper.updateById(obj);
- return this.userMapper.selectById(obj.getId());
- }
-
- //删除缓存
- @CacheEvict(key = "#id")
- public void deleteUser(Integer id){
- QueryWrapper<User> userQueryWrapper = new QueryWrapper<>();
- userQueryWrapper.eq("id",id);
- this.userMapper.delete(userQueryWrapper);
- }
- }
4 测试类编写
- import cn.jiqistudy.redis_1.Redis1Application;
- import cn.jiqistudy.redis_1.pojo.User;
- import cn.jiqistudy.redis_1.service.UserService;
- import org.junit.Test;
- import org.junit.runner.RunWith;
- import org.springframework.beans.factory.annotation.Autowired;
- import org.springframework.boot.test.context.SpringBootTest;
- import org.springframework.test.context.junit4.SpringRunner;
-
- @RunWith(SpringRunner.class)
- @SpringBootTest(classes = Redis1Application.class)
- public class Test_7 {
-
- @Autowired
- private UserService userService;
-
- //将查询的结果,缓存起来
- @Test
- public void fangfa1()
- {
- User userById = userService.findUserById(2);
- System.out.println(userById);
- }
-
- //同时更新数据库和缓存
- @Test
- public void fangfa2()
- {
- User user = new User(2,"李盛霖","男1",15,"地球");
- userService.updateUser(user);
- }
-
- //同时删除数据库记录和缓存
- @Test
- public void fangfa3()
- {
- userService.deleteUser(1);
- }
- }
详细说明
#### @CacheConfig
@CacheConfig是类级别的注解,统一该类的所有缓存前缀。
```
@CacheConfig(cacheNames = { "user" })
public class UserService {
```
以上代码,代表了该类的所有缓存可以都是"user::"为前缀
#### @Cacheable
@Cacheable是方法级别的注解,用于将方法的结果缓存起来。
```
@Cacheable(key="#id")
public User findUserById(Integer id){
return this.userMapper.selectByPrimaryKey(id);
}
```
以上方法被调用时,先从缓存中读取数据,如果缓存没有找到数据,再执行方法体,最后把返回值添加到缓存中。
注意:@Cacheable 一般是配合@CacheConfig一起使用的
例如上文的@CacheConfig(cacheNames = { "user" }) 和 @Cacheable(key="#id")一起使用时。
调用方法传入id=100,那redis对应的key=user::100 ,value通过采用GenericJackson2JsonRedisSerializer序列化为json
调用方法传入id=200,那redis对应的key=user::200 ,value通过采用GenericJackson2JsonRedisSerializer序列化为json
#### @CachePut
@CachePut是方法级别的注解,用于更新缓存。
```
@CachePut(key = "#obj.id")
public User updateUser(User obj){
this.userMapper.updateByPrimaryKeySelective(obj);
return this.userMapper.selectByPrimaryKey(obj.getId());
}
```
以上方法被调用时,先执行方法体,然后springcache通过返回值更新缓存,即key = "#obj.id",value=User
#### @CacheEvict(key = "#id")
@CachePut是方法级别的注解,用于删除缓存。
```
public void deleteUser(Integer id){
User user=new User();
user.setId(id);
user.setDeleted((byte)1);
this.userMapper.updateByPrimaryKeySelective(user);
}
```
以上方法被调用时,先执行方法体,在通过方法参数删除缓存
### springcache的大坑
1. 对于redis的缓存,springcache只支持String,其他的Hash 、List、set、ZSet都不支持,
所以对于Hash 、List、set、ZSet只能用RedisTemplate
2. 对于多表查询的数据缓存,springcache是不支持的,只支持单表的简单缓存。
对于多表的整体缓存,只能用RedisTemplate。
Copyright © 2003-2013 www.wpsshop.cn 版权所有,并保留所有权利。