需要的jar
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-data-redis</artifactId>
</dependency>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-aop</artifactId>
</dependency>
自定义注解
//添加缓存
@Target(ElementType.METHOD)//声明注解使用的位置
@Retention(RetentionPolicy.RUNTIME)
public @interface SaveRedisCache {
//可以加属性
//public String/int/... value();
}
//移除缓存
@Target(ElementType.METHOD)
@Retention(RetentionPolicy.RUNTIME)
public @interface RemoveRedisCache {
//可以加属性
//public String/int/... value();
}
基于切方法
@Configuration
@Aspect//声明当前类是一个切面供容器读取
public class RedisCache {
@Autowired
private RedisTemplate redisTemplate;
@Autowired
private StringRedisTemplate stringRedisTemplate;
@Around("execution(* com.baidu.service.*.select*(..))")
public Object around(ProceedingJoinPoint proceedingJoinPoint) throws Throwable {
RedisSerializer stringSerializer = new StringRedisSerializer();
redisTemplate.setKeySerializer(stringSerializer);
redisTemplate.setHashKeySerializer(stringSerializer);
StringBuilder sb = new StringBuilder();
//获取类名
String className = proceedingJoinPoint.getTarget().getClass().getName();
sb.append(className);
//获取方法名
String methodName = proceedingJoinPoint.getSignature().getName();
sb.append(methodName);
//获取所有的参数
Object[] args = proceedingJoinPoint.getArgs();
for (Object arg : args) {
sb.append(arg);
}
String s = sb.toString();
ValueOperations valueOperations = redisTemplate.opsForValue();
Object result = null;
if(redisTemplate.hasKey(s)){
result = valueOperations.get(s);
}else{
result = proceedingJoinPoint.proceed();
valueOperations.set(s,result);
}
return result;
}
@After("execution(* com.baidu.service.*.delete*(..))")
public void after(JoinPoint joinPoint){
Set<String> keys = stringRedisTemplate.keys("*");
for (String key : keys) {
stringRedisTemplate.delete(key);
}
}
注意:
发现key值出现 \xac\xed\x00\x05t\x00\tb,redisTemplate 默认的序列化方式为 jdkSerializeable, StringRedisTemplate的默认序列化方式为StringRedisSerializer
基于切自定义注解
@Configuration//当前类为配置类
@Aspect//作用是把当前类标识为一个切面供容器读取
public class RedisCache {
@Autowired
private RedisTemplate redisTemplate;
@Around("@annotation(com.baidu.annotation.SaveRedisCache)")
public Object arround(ProceedingJoinPoint proceedingJoinPoint) throws Throwable {
StringBuilder sb = new StringBuilder();
//获取类名
String className = proceedingJoinPoint.getTarget().getClass().getName();
//获取方法名
String methodName = proceedingJoinPoint.getSignature().getName();
sb.append(methodName);
//获取所有的参数
Object[] args = proceedingJoinPoint.getArgs();
for (Object arg : args) {
sb.append(arg);
}
String s = sb.toString();
HashOperations hashOperations = redisTemplate.opsForHash();
Boolean aBoolean = redisTemplate.hasKey(className);
Object result = null;
if(aBoolean){
result = hashOperations.get(className,s);
}else {
result = proceedingJoinPoint.proceed();
HashMap<String, Object> map = new HashMap<>();
map.put(s, result);
hashOperations.putAll(className, map);
redisTemplate.expire(className,10, TimeUnit.SECONDS);
}
return result;
}
@After("@annotation(com.baidu.annotation.RemoveRedisCache)")
public void after(JoinPoint joinPoint){
String className = joinPoint.getTarget().getClass().getName();
redisTemplate.delete(className);
}