配置yml
或者添加到对应的properties都是可以的
redis:
host: localhot
port: 6379
password: 123456
引入redis对应的jar
<dependency> <groupId>org.springframework.boot</groupId> <artifactId>spring-boot-starter-data-redis</artifactId> </dependency> <dependency> <groupId>com.alibaba</groupId> <artifactId>fastjson</artifactId> <version>1.2.83</version> </dependency> <dependency> <groupId>com.google.code.gson</groupId> <artifactId>gson</artifactId> <version>2.8.5</version> </dependency>
启动本地redis
RedisDesktopManager本地连接查看下对应的redis
可视化客户端解压即用。博文附带可视化客户端、
连接成功
现在我们看到里面有两个key值,k1和password
RedisTemplate新增一条数据
我现在新增一个key为redis1
乱码
但是新增完之后明显是乱码,这时候我们需要对RedisTemplate进行序列化操作
序列化RedisTemplate
方便我们后续对RedisTemplate的操作,单独操作RedisTemplate太麻烦,太繁琐。
import com.fasterxml.jackson.annotation.JsonAutoDetect; import com.fasterxml.jackson.annotation.PropertyAccessor; import com.fasterxml.jackson.databind.ObjectMapper; import org.springframework.context.annotation.Bean; import org.springframework.context.annotation.Configuration; import org.springframework.data.redis.connection.RedisConnectionFactory; import org.springframework.data.redis.core.RedisTemplate; import org.springframework.data.redis.serializer.Jackson2JsonRedisSerializer; import org.springframework.data.redis.serializer.StringRedisSerializer; /** * redisConfig配置 */ @Configuration public class RedisConfig { /** * 初始化RedisTemplate 模版序列化操作 * * @param factory * @return */ @Bean public RedisTemplate redisTemplate(RedisConnectionFactory factory) { // 我们为了自己开发方便,一般直接使用 <String, Object> RedisTemplate<String, Object> template = new RedisTemplate<>(); template.setConnectionFactory(factory); // Json序列化配置 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); // String 的序列化 StringRedisSerializer stringRedisSerializer = new StringRedisSerializer(); // key采用String的序列化方式 template.setKeySerializer(stringRedisSerializer); // hash的key也采用String的序列化方式 template.setHashKeySerializer(stringRedisSerializer); // value序列化方式采用jackson template.setValueSerializer(jackson2JsonRedisSerializer); // hash的value序列化方式采用jackson template.setHashValueSerializer(jackson2JsonRedisSerializer); template.afterPropertiesSet(); return template; } }
再次执行写入redis,数据正常
RedisTemplate进行封装。
service
import java.util.List; import java.util.Map; /** * Redis操作 * * @author ex_yangqiusheng * @Date 2020-5-19 19:19:30 */ public interface RedisService { /** * 设置给定 key 的值并设置时间 * 如果 key 已经存储其他值, SET 就覆写旧值 * * @param key 键 * @param value 值 * @param time 时间(秒) time要大于0 ; time等于-1 将设置无限期 * @return true成功 false 失败 */ boolean set(String key, Object value, long time); /** * 设置给定 key 的值并设置时间 * 如果 key 已经存储其他值, SET 就覆写旧值 * 默认无限期 * * @param key 键 * @param value 值 * @return true成功 false 失败 */ boolean set(String key, Object value); /** * 获取指定 key 的值。 * 如果 key 不存在,返回 null * * @param key * @param clazz 需要转换的对象,不需要转换时,为null * @return 返回 key 的值,如果 key 不存在时,返回 null */ <T> T get(String key, Class<T> clazz); /** * 删除缓存 * 删除已存在的键。不存在的 key 会被忽略 * * @param key 可以传一个值 或多个 * @return 被删除 key 的数量 */ boolean delete(String... key); /** * 指定缓存失效时间 * * @param key 键 * @param time 时间(秒) * @return */ boolean expire(String key, long time); /** * 根据key 获取过期时间 * * @param key 键 不能为null * @return 时间(秒) 返回0代表为永久有效 */ long getExpireByKey(String key); /** * 哈希表中的字段赋值 * 如果哈希表不存在,一个新的哈希表被创建并进行 HSET 操作。 * 如果字段已经存在于哈希表中,旧值将被覆盖。 * * @param key 主键KEY * @param item 细项 * @param value 值 * @param time 时间(秒) 注意:如果已存在的hash表有时间,这里将会替换原有的时间 * @return true 成功 false失败 */ boolean setHash(String key, String item, Object value, long time); /** * 哈希表中的字段赋值 * 如果哈希表不存在,一个新的哈希表被创建并进行 HSET 操作。 * 如果字段已经存在于哈希表中,旧值将被覆盖。 * * @param key 主键KEY * @param item 细项 * @param value 值 * @return true 成功 false失败 */ boolean setHash(String key, String item, Object value); /** * 返回哈希表中指定字段的值 * * @param key 键 * @param item 项 * @param clazz 需要转换的对象,不需要转换时,为null * @return 返回给定字段的值。如果给定的字段或 key 不存在时,返回 null 。 */ <T> T getHash(String key, String item, Class<T> clazz); /** * 同时将多个 field-value (字段-值)对设置到哈希表中。 * 此命令会覆盖哈希表中已存在的字段。 * 如果哈希表不存在,会创建一个空哈希表,并执行 HMSET 操作。 * * @param key 键 * @param map 对应多个键值 * @param time 时间(秒) * @return true成功 false失败 */ boolean setMap(String key, Map<String, Object> map, long time); /** * 同时将多个 field-value (字段-值)对设置到哈希表中。 * 此命令会覆盖哈希表中已存在的字段。 * 如果哈希表不存在,会创建一个空哈希表,并执行 HMSET 操作。 * * @param key 键 * @param map 对应多个键值 * @return true成功 false失败 */ boolean setMap(String key, Map<String, Object> map); /** * 获取hashKey对应的所有键值 * * @param key 键 * @return 以列表形式返回哈希表的字段及字段值。 若 key 不存在,返回空列表。 */ Map<Object, Object> getMap(String key); /** * 从列表左边存入缓存并设置时间 * * @param key 键 * @param list 值 * @param time 时间(秒) * @return */ <T> long setListLeftPushAll(String key, List<T> list, long time); /** * 从列表左边存入缓存并设置时间 * * @param key 键 * @param list 值 * @return */ <T> long setListLeftPushAll(String key, List<T> list); /** * 从列表右边存入缓存并设置时间 * * @param key 键 * @param list 值 * @return */ <T> long setListRightPushAll(String key, List<T> list); /** * 从列表右边存入缓存并设置时间 * * @param key 键 * @param list 值 * @param time 时间(秒) * @return */ <T> long setListRightPushAll(String key, List<T> list, long time); /** * 获取list缓存的内容 * * @param key 键 * @param start 开始 0 是第一个元素 * @param end 结束 -1代表所有值 * @return 一个列表,包含指定区间内的元素 * @取出来的元素 总数 end-start+1 */ <T> List<T> getList(String key, long start, long end); /** * 获取list缓存的内容(所有) * * @param key 键 * @return 一个列表,包含指定区间内的元素 */ <T> List<T> getList(String key); /** * 获取list缓存的内容(所有) * * @param clazz 返回对象 * @param key 键 * @return 一个列表,包含指定区间内的元素 */ <T> List<T> getList(String key, Class<T> clazz); }
注:封装对应的方法,再上面最好加上对应的自己封装的异常会更好一些
例如
boolean set(String key, Object value, long time) throws BussinessException;
impl
import CommonFunctions; import RedisConstans; import RedisService; import cn.axa.ruleengine.modules.redis.utils.JSONUtils; import lombok.extern.slf4j.Slf4j; import org.springframework.beans.factory.annotation.Autowired; import org.springframework.data.redis.core.RedisTemplate; import org.springframework.stereotype.Service; import org.springframework.util.CollectionUtils; import java.util.HashMap; import java.util.List; import java.util.Map; import java.util.concurrent.TimeUnit; ; /** * Redis实现 * * @author ex_yangqiusheng * @Date 2020-5-20 21:23:37 */ @Slf4j @Service public class RedisServiceImpl implements RedisService { @Autowired private RedisTemplate redisTemplate; /** * 设置给定 key 的值并设置时间 * 如果 key 已经存储其他值, SET 就覆写旧值 * * @param key 键 * @param value 值 * @param time 时间(秒) time要大于0 ; time等于-1 将设置无限期 * @return true成功 false 失败 */ @Override public boolean set(String key, Object value, long time) { try { // Object stringValue = ""; // if (!CommonFunctions.isEmpty(value) && !RedisConstans.isBaseType(value)) { // stringValue = RedisConstans.getStringValue(value); // } else { // stringValue = value; // } redisTemplate.opsForValue().set(key, value); expire(key, time); return true; } catch (Exception e) { log.error(RedisConstans.REDIS_ERROR + key, e); return false; } } @Override public boolean set(String key, Object value) { try { // Object stringValue = ""; // if (!CommonFunctions.isEmpty(value) && !RedisConstans.isBaseType(value)) { // stringValue = RedisConstans.getStringValue(value); // } else { // stringValue = value; // } redisTemplate.opsForValue().set(key, value); return true; } catch (Exception e) { log.error(RedisConstans.REDIS_ERROR + key, e); return false; } } /** * 获取指定 key 的值。 * 如果 key 不存在,返回 null * * @param key * @param clazz 需要转换的对象,不需要转换时,为null * @return 返回 key 的值,如果 key 不存在时,返回 null */ @Override public <T> T get(String key, Class<T> clazz) { try { Object o = redisTemplate.opsForValue().get(key); // Object resultObject = RedisConstans.getObject(clazz, o); return (T) o; } catch (Exception e) { log.error(RedisConstans.REDIS_ERROR + key, e); return null; } } /** * 删除缓存 * 删除已存在的键。不存在的 key 会被忽略 * * @param key 可以传一个值 或多个 * @return 被删除 key 的数量 */ @Override public boolean delete(String... key) { try { if (!CommonFunctions.isEmpty(key) && key.length > 0) { if (key.length == 1) { redisTemplate.delete(key[0]); } else { redisTemplate.delete(CollectionUtils.arrayToList(key)); } } return true; } catch (Exception e) { log.error(RedisConstans.REDIS_ERROR + key, e); return false; } } /** * 指定缓存失效时间 * * @param key 键 * @param time 时间(秒) * @return */ @Override public boolean expire(String key, long time) { try { if (time > 0) { redisTemplate.expire(key, time, TimeUnit.SECONDS); } return true; } catch (Exception e) { log.error(RedisConstans.REDIS_ERROR + key, e); return false; } } /** * 根据key 获取过期时间 * * @param key 键 不能为null * @return 时间(秒) 返回0代表为永久有效 */ @Override public long getExpireByKey(String key) { return redisTemplate.getExpire(key, TimeUnit.SECONDS); } @Override public boolean setHash(String key, String item, Object value, long time) { try { String stringValue = ""; if (!CommonFunctions.isEmpty(value)) { stringValue = RedisConstans.getStringValue(value); } redisTemplate.opsForHash().put(key, item, stringValue); expire(key, time); return true; } catch (Exception e) { log.error(RedisConstans.REDIS_ERROR + key + item, e); return false; } } @Override public boolean setHash(String key, String item, Object value) { try { // String stringValue = ""; // if (!CommonFunctions.isEmpty(value)) { // stringValue = RedisConstans.getStringValue(value); // } redisTemplate.opsForHash().put(key, item, value); return true; } catch (Exception e) { log.error(RedisConstans.REDIS_ERROR + key + item, e); return false; } } @Override public <T> T getHash(String key, String item, Class<T> clazz) { try { Object o = redisTemplate.opsForHash().get(key, item); // Object resultObject = RedisConstans.getObject(clazz, o); // return (T) resultObject; return (T) o; } catch (Exception e) { log.error(RedisConstans.REDIS_ERROR + key + item, e); return null; } } @Override public boolean setMap(String key, Map<String, Object> map, long time) { try { Map mapValue = new HashMap(); if (map.size() != 0) { mapValue = RedisConstans.getMapValue(map); } redisTemplate.opsForHash().putAll(key, mapValue); expire(key, time); return true; } catch (Exception e) { log.error(RedisConstans.REDIS_ERROR + key, e); return false; } } @Override public boolean setMap(String key, Map<String, Object> map) { try { Map mapValue = new HashMap(); if (map.size() != 0) { mapValue = RedisConstans.getMapValue(map); } redisTemplate.opsForHash().putAll(key, mapValue); return true; } catch (Exception e) { log.error(RedisConstans.REDIS_ERROR + key, e); return false; } } @Override public Map<Object, Object> getMap(String key) { return redisTemplate.opsForHash().entries(key); } @Override public <T> long setListLeftPushAll(String key, List<T> list, long time) { try { //先删除该集合KEY值 this.delete(key); List<String> listValue = null; //添加最新数据 if (CommonFunctions.isNotEmpty(list)) { listValue = RedisConstans.getListValue(list); } Long count = redisTemplate.opsForList().leftPushAll(key, listValue); expire(key, time); return count; } catch (Exception e) { log.error(RedisConstans.REDIS_ERROR + key, e); return 0; } } @Override public <T> long setListLeftPushAll(String key, List<T> list) { try { //先删除该集合KEY值 this.delete(key); List<String> listValue = null; //添加最新数据 if (CommonFunctions.isNotEmpty(list)) { listValue = RedisConstans.getListValue(list); } Long count = redisTemplate.opsForList().leftPushAll(key, listValue); return count; } catch (Exception e) { log.error(RedisConstans.REDIS_ERROR + key, e); return 0; } } @Override public <T> long setListRightPushAll(String key, List<T> list) { try { //先删除该集合KEY值 this.delete(key); List<String> listValue = null; //添加最新数据 if (CommonFunctions.isNotEmpty(list)) { listValue = RedisConstans.getListValue(list); } Long count = redisTemplate.opsForList().rightPushAll(key, listValue); return count; } catch (Exception e) { log.error(RedisConstans.REDIS_ERROR + key, e); return 0; } } @Override public <T> long setListRightPushAll(String key, List<T> list, long time) { try { //先删除该集合KEY值 this.delete(key); List<String> listValue = null; //添加最新数据 if (CommonFunctions.isNotEmpty(list)) { listValue = RedisConstans.getListValue(list); } Long count = redisTemplate.opsForList().rightPushAll(key, list); expire(key, time); return count; } catch (Exception e) { log.error(RedisConstans.REDIS_ERROR + key, e); return 0; } } @Override public <T> List<T> getList(String key, long start, long end) { try { if (CommonFunctions.isNotEmpty(key)) { return redisTemplate.opsForList().range(key, start, end); } } catch (Exception e) { log.error(RedisConstans.REDIS_ERROR + key, e); return null; } return null; } @Override public <T> List<T> getList(String key) { try { if (CommonFunctions.isNotEmpty(key)) { return redisTemplate.opsForList().range(key, 0, -1); } } catch (Exception e) { log.error(RedisConstans.REDIS_ERROR + key, e); return null; } return null; } @Override public <T> List<T> getList(String key, Class<T> clazz) { try { if (CommonFunctions.isNotEmpty(key)) { List<Object> list = getList(key); if (CommonFunctions.isNotEmpty(list)) { return JSONUtils.JsonToClass(list, clazz); } } } catch (Exception e) { log.error(RedisConstans.REDIS_ERROR + key, e); return null; } return null; } }
工具类CommonFunctions,常量RedisConstans,JSONUtils
import lombok.extern.slf4j.Slf4j; import java.io.ByteArrayInputStream; import java.io.ByteArrayOutputStream; import java.io.ObjectInputStream; import java.io.ObjectOutputStream; import java.util.List; import java.util.Map; import java.util.Set; /** * 验空Utils */ @Slf4j public class CommonFunctions { /** * 判空方法 * * @param object * @return */ public static boolean isEmpty(Object object) { if (object == null || object.toString().trim().length() == 0) { return true; } else { return false; } } /** * 判空方法 * * @param list * @return */ public static boolean isEmpty(List list) { if (list == null || list.isEmpty()) { return true; } else { return false; } } /** * 判空方法 * * @param object * @return */ public static boolean isNotEmpty(Object object) { if (object == null || object.toString().trim().length() == 0) { return false; } else { return true; } } /** * 判空方法 * * @param list * @return */ public static boolean isNotEmpty(List list) { if (list == null || list.isEmpty()) { return false; } else { return true; } } /** * 判空方法 * * @param set * @return */ public static boolean isNotEmpty(Set set) { if (set == null || set.isEmpty()) { return false; } else { return true; } } /** * 判空方法 * * @param set * @return */ public static boolean isEmpty(Set set) { if (set == null || set.isEmpty()) { return true; } else { return false; } } /** * 判空方法 * * @param map * @return */ public static boolean isEmpty(Map map) { if (map == null || map.isEmpty()) { return true; } else { return false; } } /** * 判空方法 * * @param map * @return */ public static boolean isNotEmpty(Map map) { if (map == null || map.isEmpty()) { return false; } else { return true; } } /** * 对象克隆方法 * * @param bean * @return */ public static Object getCloneObject(Object bean) { Object cloneBean = null; try { ByteArrayOutputStream byout = new ByteArrayOutputStream(); ObjectOutputStream obj = new ObjectOutputStream(byout); obj.writeObject(bean); ByteArrayInputStream byin = new ByteArrayInputStream(byout.toByteArray()); ObjectInputStream ins = new ObjectInputStream(byin); cloneBean = (Object) ins.readObject(); } catch (Exception ex) { ex.printStackTrace(); } return cloneBean; } /** * 对象转byte * @param obj * @return */ public static byte[] ObjectToByte(Object obj) { byte[] bytes = null; try { // object to bytearray ByteArrayOutputStream bo = new ByteArrayOutputStream(); ObjectOutputStream oo = new ObjectOutputStream(bo); oo.writeObject(obj); bytes = bo.toByteArray(); bo.close(); oo.close(); } catch (Exception e) { log.error("对象转byte" + e.getMessage()); e.printStackTrace(); } return bytes; } /** * byte转对象 * @param bytes * @param obj * @return */ public static Object ByteToObject(Object obj,byte[] bytes) { try { // bytearray to object ByteArrayInputStream bi = new ByteArrayInputStream(bytes); ObjectInputStream oi = new ObjectInputStream(bi); obj = (Object) oi.readObject(); bi.close(); oi.close(); } catch (Exception e) { log.error("byte转对象" + e.getMessage()); e.printStackTrace(); } return obj; } }
import com.alibaba.fastjson.JSON; import com.alibaba.fastjson.JSONObject; import javax.annotation.PostConstruct; import java.util.*; /** * redis常量 */ public final class RedisConstans { /** * 失效时间---永久有效 */ public static final long MINUS_ONE = -1L; /** * 失效时间---一个月 */ public static final long MONTH_ONE = 97200L; /** * 失效时间---两个小时 */ public static final long HOUR_TWO = 7200L; /** * ********** */ public static final String DECISION_EXCEL_CACHE = "**********"; /** * ********** */ public static final String REDIS_ERROR = "[ ********** ] : "; /** * 常量1 */ public static final String REDIS_ONE = "1"; /** * 常量2 */ public static final String REDIS_TWO = "2"; /** * 常量0 */ public static final String REDIS_ZERO = "0"; /** * ********** */ public static final String REDIS_CACHE_NAME = "**********:"; /** * ********** */ public static final String REDIS_CACHE_CALIB_NAME = "**********:**********"; /** * ********** */ public static final String REDIS_CACHE_CALIB_COMMON_NAME = "**********:**********"; /** * ********** */ public static final String REDIS_CACHE_DEPARTMENT_NAME = "**********:**********"; /** * ********** */ public static final String REDIS_CACHE_DEPARTMENT_UPPER_NAME = "**********:**********:**********"; /** * ********** */ public static final String REDIS_CACHE_COMMON_DEPARTMENT_NAME = "**********:**********:**********"; /** * ********** */ public static final String REDIS_CACHE_NEWRULEENGINE = "**********_"; /** * ********** */ public static final String PRE_CACHE_NEWRULEENGINE = "PRE"; /** * redis拼接KEY ver+ID * * @param ver * @param key * @return */ @PostConstruct public static String cacheName(String ver, Long key) { return ver + "_" + key; } /** * redis数据KEY * * @param key * @return */ public static String cacheName(Long key, Boolean isPerEffect) { if (isPerEffect){ return PRE_CACHE_NEWRULEENGINE + REDIS_CACHE_NEWRULEENGINE + key; } return REDIS_CACHE_NEWRULEENGINE + key; } /** * 对象转json字符串 * * @param object 存入对象 * @return */ public static String getStringValue(Object object) { String stringValue = JSON.toJSONString(object); return stringValue; } /** * json字符串转对象 * * @param clazz 接收对象 * @param value 缓存对象 * @param clazz 需要转换的对象,不需要转换时,为null * @return */ public static <T> T getObject(Class<T> clazz, Object value) { if (clazz != null && value != null) { JSONObject jsonObject = JSON.parseObject(value.toString()); return JSON.toJavaObject(jsonObject, clazz); } return (T) value; } /** * 判断object是否为基本类型 * * @param object * @return */ public static boolean isBaseType(Object object) { Class className = object.getClass(); if (className.equals(Integer.class) || className.equals(Byte.class) || className.equals(Long.class) || className.equals(Double.class) || className.equals(Float.class) || className.equals(Character.class) || className.equals(Short.class) || className.equals(Boolean.class)) { return true; } return false; } /** * 将Map中的对象转为json字符串 * * @param map 存入对象 * @return */ public static Map getMapValue(Map map) { Map valueMap = new HashMap(); Iterator it = map.keySet().iterator(); while (it.hasNext()) { String mapKey = it.next().toString(); String mapValue = JSON.toJSONString(map.get(mapKey)); valueMap.put(mapKey, mapValue); } return valueMap; } /** * 将List中的对象转为json字符串 * * @param list 存入对象 * @return */ public static List<String> getListValue(List list) { List<String> listStr = new ArrayList<>(list.size()); for (int i = 0; i < list.size(); i++) { String str = JSON.toJSONString(list.get(i)); listStr.add(i, str); } return listStr; } }
import CommonFunctions; import com.alibaba.fastjson.JSONObject; import com.google.gson.Gson; import com.google.gson.reflect.TypeToken; import lombok.extern.slf4j.Slf4j; import java.lang.reflect.Type; import java.util.Arrays; import java.util.Collection; import java.util.List; import java.util.stream.Collectors; /** * JsonUtils */ @Slf4j public class JSONUtils { /** * json转对应对象 * * @param valueList 转值对象 * @param clazz 类型 * @param <T> 返回类型 * @return */ public static <T> List<T> JsonToClass(List<Object> valueList, Class<T> clazz) { try { if (CommonFunctions.isNotEmpty(valueList)) { List<Object> collect = valueList.stream().map(v -> { T t = jsonToBean(v.toString(), clazz); return t; }).collect(Collectors.toList()); } } catch (Exception e) { log.error(e.getMessage(), e); } return null; } /** * json字符串转bean对象 * @param json * @param clazz * @param <T> * @return */ public static <T> T jsonToBean(String json, Class<T> clazz) { if (CommonFunctions.isNotEmpty(json) && CommonFunctions.isNotEmpty(clazz)) { try { T newInstance = clazz.newInstance(); return (T) JSONObject.parseObject(json, newInstance.getClass()); } catch (Exception e) { log.error(e.getMessage(), e); return null; } } return null; } public static String toJson(Object obj) { Gson gson = new Gson(); return gson.toJson(obj); } public static String toJson(Object obj, Type type) { Gson gson = new Gson(); return gson.toJson(obj, type); } public static String toJson(Collection collection) { Gson gson = new Gson(); return gson.toJson(collection); } public static String toJson(Collection collection, Type type) { Gson gson = new Gson(); return gson.toJson(collection, type); } public static <T> T toObject(String json, Type type) { Gson gson = new Gson(); return (T) gson.fromJson(json, type); } public static <T> List<T> toObject(String jsonString, Class<T[]> type) { Gson gson = new Gson(); T[] list = gson.fromJson(jsonString, type); return Arrays.asList(list); } public static <T> T toObject(String json, TypeToken<T> token) { Gson gson = new Gson(); return (T) gson.fromJson(json, token.getType()); } }
验证
测试成功!上面代码即办即用。感谢大家三连