使用注解+springEL表达式+Aspect实现简单的缓存处理
程序员文章站
2022-03-21 07:56:08
使用注解+springEL表达式+Aspect实现简单的缓存处理话不多说,直接上代码:注解类:RedisCache.java/** * @author: Administrator * 此注解是用来 实现 redis 缓存用的 * 在方法上面使用 */@Target(ElementType.METHOD)@Retention(RetentionPolicy.RUNTIME)@Documentedpublic @interface RedisCache { /**...
使用注解+springEL表达式+Aspect实现简单的缓存处理
话不多说,直接上代码:
注解类:
RedisCache.java
/**
* @author: Administrator
* 此注解是用来 实现 redis 缓存用的
* 在方法上面使用
*/
@Target(ElementType.METHOD)
@Retention(RetentionPolicy.RUNTIME)
@Documented
public @interface RedisCache {
/**
* 保存到 Redis 中的 key
* 这个 属性 使用 ParserContext.TEMPLATE_EXPRESSION 的形式进行解析
* @return
*/
String cacheKey() default "";
/**
* 需要缓存的 值
* @return
*/
String cacheValue() default "";
/**
* 是否是 批量操作
* @return
*/
boolean batch() default false;
/**
* 批量操作时,每一项 的名称
* @return
*/
String itemName() default "item";
}
切面类:
RedisCacheAspect.java
/**
* @author: Administrator
*/
@Component
@Aspect
public class RedisCacheAspect {
@Autowired
private RedisUtil redisUtil;
private static final ExpressionParser parser = new SpelExpressionParser();
/**
* 插入缓存
* @param joinPoint
* @param redisCache
*/
@Before("@annotation(redisCache)")
public void insertCache(JoinPoint joinPoint,RedisCache redisCache){
// 获取参数
Object[] args = joinPoint.getArgs();
// 获取参数名字
MethodSignature methodSignature = (MethodSignature)joinPoint.getSignature();
String[] parameterNames = methodSignature.getParameterNames();
// 获取 EvaluationContext
StandardEvaluationContext evaluationContext = getEvaluationContext(parameterNames, args);
// 获取 redis 存储 key
if(!redisCache.batch()){
String cacheKey = redisCache.cacheKey();
String cacheValue = redisCache.cacheValue();
// 解析 redis key
Expression keyExpression = parser.parseExpression(cacheKey,ParserContext.TEMPLATE_EXPRESSION);
String key = keyExpression.getValue(evaluationContext, String.class);
// 解析 值
Expression valueExpression = parser.parseExpression(cacheValue);
Object value = valueExpression.getValue(evaluationContext);
// 存入 缓存
redisUtil.setKey(key,value);
}else{
// 获取 迭代对象
String batchValue = redisCache.cacheValue();
String itemName = redisCache.itemName();
String cacheKey = redisCache.cacheKey();
Iterable value = parser.parseExpression(batchValue).getValue(evaluationContext, Iterable.class);
// 迭代生成 缓存
for(Object it: value){
evaluationContext.setVariable(itemName,it);
// 解析 key
String redisCacheKey = parser.parseExpression(cacheKey,ParserContext.TEMPLATE_EXPRESSION).getValue(evaluationContext, String.class);
redisUtil.setKey(redisCacheKey,it);
}
}
}
public StandardEvaluationContext getEvaluationContext(String[] parameterNames,Object[] args){
StandardEvaluationContext context = new StandardEvaluationContext();
for(int i = 0; i< parameterNames.length ; i++){
// 设置参数
context.setVariable(parameterNames[i],args[i]);
}
return context;
}
}
Service类
CacheService.java
/**
* @author: Administrator
*/
@Service
public class CacheService {
/**
* 单个 数据 缓存
* @param param1
* @param user
*/
@RedisCache(cacheKey = "redis:cache:user:#{#user.uuid}",cacheValue = "#user")
public void insertCache(String param1, User user){
System.out.println("进入方法:insertCache");
}
/**
* 批量数据 缓存
* @param userList
*/
@RedisCache(cacheKey = "redis:cache:user:#{#perItem.uuid}",cacheValue = "#userList",batch = true,itemName = "perItem")
public void insertCacheBatch(List<User> userList){
}
}
User类
User.java
/**
* @author: Administrator
* 实体类, 测试用
*/
public class User {
/**
* 用户Id
*/
private String uuid;
/**
* 用户名字
*/
private String name;
/**
* 年龄
*/
private Integer age;
/**
* 性别
*/
private String sex;
public String getUuid() {
return uuid;
}
public void setUuid(String uuid) {
this.uuid = uuid;
}
public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
public Integer getAge() {
return age;
}
public void setAge(Integer age) {
this.age = age;
}
public String getSex() {
return sex;
}
public void setSex(String sex) {
this.sex = sex;
}
@Override
public String toString() {
return "User{" +
"uuid='" + uuid + '\'' +
", name='" + name + '\'' +
", age=" + age +
", sex='" + sex + '\'' +
'}';
}
Redis工具类
RedisUtil.java
package ultraman.util;
import com.fasterxml.jackson.databind.ObjectMapper;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.boot.test.context.TestComponent;
import org.springframework.data.redis.core.RedisTemplate;
import org.springframework.stereotype.Component;
import org.springframework.util.CollectionUtils;
import ultraman.test.SpringTest;
import java.util.Collections;
import java.util.List;
import java.util.Map;
import java.util.Set;
import java.util.concurrent.TimeUnit;
/**
* @author: Administrator
*/
@Component
public class RedisUtil {
private static final Logger logger = LoggerFactory.getLogger(RedisUtil.class);
@Autowired
private RedisTemplate<String,Object> redisTemplate;
/**
* 设置 redis 键的过期时间
* @param key
* @param time
* @return
*/
//###########################Common Begin###########################
public boolean expire(String key,long time){
try{
if(time > 0){
redisTemplate.expire(key,time, TimeUnit.SECONDS);
return true;
}else{
logger.info("过期时间设置必须大于0");
return false;
}
}catch (Exception e){
logger.info("设置key[{}]过期时间出现异常,异常信息:[{}]",key,e.getMessage());
return false;
}
}
/**
* 获取 键的 过期时间(秒), 0代表永久有效
* @param key
* @return
*/
public long getExpire(String key){
return redisTemplate.getExpire(key,TimeUnit.SECONDS);
}
/**
* 判断 键值是否存在
* @param key
* @return
*/
public boolean hasKey(String key){
return redisTemplate.hasKey(key);
}
/**
* 删除 键值
* @param keys
*/
public void deleteKey(String... keys){
if(null ==keys || keys.length > 0){
logger.info("键值不能为空");
return;
}
try{
// 删除 键 可以 是一个 List
redisTemplate.delete(CollectionUtils.arrayToList(keys));
}catch (Exception e){
logger.error("删除键值出现异常,异常信息:[{}]",e.getMessage());
}
}
//###########################Common End###########################
//###########################String Begin###########################
/**
* 获取数据
* @param key
* @return
*/
public Object getKey(String key){
return key == null ? null : redisTemplate.opsForValue().get(key);
}
/**
* 设置缓存
* @param key
* @param object
* @return
*/
public boolean setKey(String key,Object object){
try{
redisTemplate.opsForValue().set(key,object);
return true;
}catch (Exception e){
logger.info("设置缓存出现异常,异常信息:[{}]",e.getMessage());
return false;
}
}
/**
* 设置 缓存的时候同时设置过期时间
* @param key
* @param value
* @param expire
* @return
*/
public boolean setKeyWithExpire(String key, Object value,long expire){
try{
redisTemplate.opsForValue().set(key,value,expire);
return true;
}catch (Exception e){
logger.info("设置缓存时出现异常,异常信息:[{}]",e.getMessage());
return false;
}
}
/**
* 递增
* @param key 键
* @param delta 要增加几(大于0)
* @return
*/
public long incr(String key, long delta) {
if (delta < 0) {
throw new RuntimeException("递增因子必须大于0");
}
// 对于不可递增类型的数据(字符串等) ,会报错
return redisTemplate.opsForValue().increment(key, delta);
}
public long decr(String key,long delta){
if(delta > 0 ){
throw new RuntimeException("递减因子必须小于0");
}
return redisTemplate.opsForValue().decrement(key,delta);
}
//###########################String End###########################
//###########################Map Begin###########################
/**
* HashGet
* @param key 键 不能为null
* @param item 项 不能为null
* @return 值
*/
public Object hashGet(String key, String item) {
return redisTemplate.opsForHash().get(key, item);
}
/**
* 获取hashKey对应的所有键值
* @param key 键
* @return 对应的多个键值
*/
public Map<Object, Object> hmget(String key) {
return redisTemplate.opsForHash().entries(key);
}
/**
* HashSet
* @param key 键
* @param map 对应多个键值
* @return true 成功 false 失败
*/
public boolean hmset(String key, Map<String, Object> map) {
try {
redisTemplate.opsForHash().putAll(key, map);
return true;
} catch (Exception e) {
logger.info("设置hash 出现异常,异常信息:[{}]",e.getMessage());
return false;
}
}
/**
* HashSet 并设置时间
* @param key 键
* @param map 对应多个键值
* @param time 时间(秒)
* @return true成功 false失败
*/
public boolean hmset(String key, Map<String, Object> map, long time) {
try {
redisTemplate.opsForHash().putAll(key, map);
if (time > 0) {
expire(key, time);
}
return true;
} catch (Exception e) {
logger.info("设置hash 出现异常,异常信息:[{}]",e.getMessage());
return false;
}
}
/**
* 向一张hash表中放入数据,如果不存在将创建
* @param key 键
* @param item 项
* @param value 值
* @return true 成功 false失败
*/
public boolean hset(String key, String item, Object value) {
try {
redisTemplate.opsForHash().put(key, item, value);
return true;
} catch (Exception e) {
logger.info("设置hash 出现异常,异常信息:[{}]",e.getMessage());
return false;
}
}
/**
* 向一张hash表中放入数据,如果不存在将创建
* @param key 键
* @param item 项
* @param value 值
* @param time 时间(秒) 注意:如果已存在的hash表有时间,这里将会替换原有的时间
* @return true 成功 false失败
*/
public boolean hset(String key, String item, Object value, long time) {
try {
redisTemplate.opsForHash().put(key, item, value);
if (time > 0) {
expire(key, time);
}
return true;
} catch (Exception e) {
logger.info("设置hash 出现异常,异常信息:[{}]",e.getMessage());
return false;
}
}
/**
* 删除hash表中的值
* @param key 键 不能为null
* @param item 项 可以使多个 不能为null
*/
public void hdel(String key, Object... item) {
redisTemplate.opsForHash().delete(key, item);
}
/**
* 判断hash表中是否有该项的值
* @param key 键 不能为null
* @param item 项 不能为null
* @return true 存在 false不存在
*/
public boolean hHasKey(String key, String item) {
return redisTemplate.opsForHash().hasKey(key, item);
}
/**
* hash递增 如果不存在,就会创建一个 并把新增后的值返回
* @param key 键
* @param item 项
* @param by 要增加几(大于0)
* @return
*/
public double hincr(String key, String item, double by) {
return redisTemplate.opsForHash().increment(key, item, by);
}
/**
* hash递减
* @param key 键
* @param item 项
* @param by 要减少记(小于0)
* @return
*/
public double hdecr(String key, String item, double by) {
return redisTemplate.opsForHash().increment(key, item, -by);
}
//###########################Map End###########################
//###########################Set Begin###########################
/**
* 根据key获取Set中的所有值
* @param key 键
* @return
*/
public Set<Object> sGet(String key) {
try {
return redisTemplate.opsForSet().members(key);
} catch (Exception e) {
e.printStackTrace();
return null;
}
}
/**
* 根据value从一个set中查询,是否存在
* @param key 键
* @param value 值
* @return true 存在 false不存在
*/
public boolean sHasKey(String key, Object value) {
try {
return redisTemplate.opsForSet().isMember(key, value);
} catch (Exception e) {
e.printStackTrace();
return false;
}
}
/**
* 将数据放入set缓存
* @param key 键
* @param values 值 可以是多个
* @return 成功个数
*/
public long sSet(String key, Object... values) {
try {
return redisTemplate.opsForSet().add(key, values);
} catch (Exception e) {
e.printStackTrace();
return 0;
}
}
/**
* 将set数据放入缓存
* @param key 键
* @param time 时间(秒)
* @param values 值 可以是多个
* @return 成功个数
*/
public long sSetAndTime(String key, long time, Object... values) {
try {
Long count = redisTemplate.opsForSet().add(key, values);
if (time > 0){
expire(key, time);
}
return count;
} catch (Exception e) {
e.printStackTrace();
return 0;
}
}
/**
* 获取set缓存的长度
* @param key 键
* @return
*/
public long sGetSetSize(String key) {
try {
return redisTemplate.opsForSet().size(key);
} catch (Exception e) {
e.printStackTrace();
return 0;
}
}
/**
* 移除值为value的
* @param key 键
* @param values 值 可以是多个
* @return 移除的个数
*/
public long setRemove(String key, Object... values) {
try {
Long count = redisTemplate.opsForSet().remove(key, values);
return count;
} catch (Exception e) {
e.printStackTrace();
return 0;
}
}
//###########################Set End###########################
//###########################List Begin###########################
/**
* 获取list缓存的内容
* @param key 键
* @param start 开始
* @param end 结束 0 到 -1代表所有值
* @return
*/
public List<Object> lGet(String key, long start, long end) {
try {
return redisTemplate.opsForList().range(key, start, end);
} catch (Exception e) {
e.printStackTrace();
return null;
}
}
/**
* 获取list缓存的长度
* @param key 键
* @return
*/
public long lGetListSize(String key) {
try {
return redisTemplate.opsForList().size(key);
} catch (Exception e) {
e.printStackTrace();
return 0;
}
}
/**
* 通过索引 获取list中的值
* @param key 键
* @param index 索引 index>=0时, 0 表头,1 第二个元素,依次类推;index<0时,-1,表尾,-2倒数第二个元素,依次类推
* @return
*/
public Object lGetIndex(String key, long index) {
try {
return redisTemplate.opsForList().index(key, index);
} catch (Exception e) {
e.printStackTrace();
return null;
}
}
/**
* 将list放入缓存
* @param key 键
* @param value 值
* @return
*/
public boolean lSet(String key, Object value) {
try {
redisTemplate.opsForList().rightPush(key, value);
return true;
} catch (Exception e) {
e.printStackTrace();
return false;
}
}
/**
* 将list放入缓存
* @param key 键
* @param value 值
* @param time 时间(秒)
* @return
*/
public boolean lSet(String key, Object value, long time) {
try {
redisTemplate.opsForList().rightPush(key, value);
if (time > 0)
expire(key, time);
return true;
} catch (Exception e) {
e.printStackTrace();
return false;
}
}
/**
* 将list放入缓存
* @param key 键
* @param value 值
* @return
*/
public boolean lSet(String key, List<Object> value) {
try {
redisTemplate.opsForList().rightPushAll(key, value);
return true;
} catch (Exception e) {
e.printStackTrace();
return false;
}
}
/**
* 将list放入缓存
*
* @param key 键
* @param value 值
* @param time 时间(秒)
* @return
*/
public boolean lSet(String key, List<Object> value, long time) {
try {
redisTemplate.opsForList().rightPushAll(key, value);
if (time > 0)
expire(key, time);
return true;
} catch (Exception e) {
e.printStackTrace();
return false;
}
}
/**
* 根据索引修改list中的某条数据
* @param key 键
* @param index 索引
* @param value 值
*/
public boolean lUpdateIndex(String key, long index, Object value) {
try {
redisTemplate.opsForList().set(key, index, value);
return true;
} catch (Exception e) {
e.printStackTrace();
return false;
}
}
/**
* 移除N个值为value
* @param key 键
* @param count 移除多少个
* @param value 值
* @return 移除的个数
*/
public long lRemove(String key, long count, Object value) {
try {
Long remove = redisTemplate.opsForList().remove(key, count, value);
return remove;
} catch (Exception e) {
e.printStackTrace();
return 0;
}
}
//###########################List End###########################
}
本文地址:https://blog.csdn.net/weixin_43389741/article/details/110878340
上一篇: 如何开发第一个Andriod程序
下一篇: 处理EditText外部区域隐藏软键盘