在SpringBoot的redisTemplate在redis当中存入数据的时候,能看到key和value被序列化,我们基本上很难判断这个缓存是干什么用的,所以我们需要修复它:
解决这个问题我们需要自定义一个序列化器RedisJsonSerializerImpl,其中还有一个内部类:
static class SerializerObject { public SerializerObject() { } public SerializerObject(String className, String jsonObject) { this.className = className; this.jsonObject = jsonObject; } private String className; private String jsonObject; public String getClassName() { return className; } public SerializerObject setClassName(String className) { this.className = className; return this; } public String getJsonObject() { return jsonObject; } public SerializerObject setJsonObject(String jsonObject) { this.jsonObject = jsonObject; return this; } @Override public String toString() { return JSON.toJSONString(this); } }
RedisJsonSerializerImpl实现了org.springframework.data.redis.serializer.RedisSerializer,并且实现下面两个方法,serialize方法定义了序列化对象(将对象从Java程序中存入缓存中),deserialize用户反序列化对象(将缓存中读取对象并转换为Java对象):
@Override public byte[] serialize(T t) throws SerializationException { // 如果对象为空,那么就返回一个空的byte数组就好了 if (null == t) return new byte[0]; // 获取序列化后的对象 String resultObject = new SerializerObject(t.getClass().getName(), JSON.toJSONString(t)).toString(); return resultObject.getBytes(StandardCharsets.UTF_8); } @Override public T deserialize(byte[] bytes) throws SerializationException { if (CollectionUtils.isNull(bytes)) return null; // 将其反序列化成一个字符串 SerializerObject resultObject = JSON.parseObject(new String(bytes, StandardCharsets.UTF_8), SerializerObject.class); try { return JSON.parseObject(resultObject.jsonObject, (Type) Class.forName(resultObject.className)); } catch (ClassNotFoundException e) { log.error("类未找到:" + resultObject.className, e); return null; } }
类完整的代码如下:
package love.xiaohh.cost.utils.storage; import com.alibaba.fastjson.JSON; import love.xiaohh.cost.utils.CollectionUtils; import org.slf4j.Logger; import org.slf4j.LoggerFactory; import org.springframework.data.redis.serializer.RedisSerializer; import org.springframework.data.redis.serializer.SerializationException; import java.lang.reflect.Type; import java.nio.charset.StandardCharsets; public class RedisJsonSerializerImplimplements RedisSerializer { private static final Logger log = LoggerFactory.getLogger(RedisJsonSerializerImpl.class); @Override public byte[] serialize(T t) throws SerializationException { // 如果对象为空,那么就返回一个空的byte数组就好了 if (null == t) return new byte[0]; // 获取序列化后的对象 String resultObject = new SerializerObject(t.getClass().getName(), JSON.toJSONString(t)).toString(); return resultObject.getBytes(StandardCharsets.UTF_8); } @Override public T deserialize(byte[] bytes) throws SerializationException { if (CollectionUtils.isNull(bytes)) return null; // 将其反序列化成一个字符串 SerializerObject resultObject = JSON.parseObject(new String(bytes, StandardCharsets.UTF_8), SerializerObject.class); try { return JSON.parseObject(resultObject.jsonObject, (Type) Class.forName(resultObject.className)); } catch (ClassNotFoundException e) { log.error("类未找到:" + resultObject.className, e); return null; } } static class SerializerObject { public SerializerObject() { } public SerializerObject(String className, String jsonObject) { this.className = className; this.jsonObject = jsonObject; } private String className; private String jsonObject; public String getClassName() { return className; } public SerializerObject setClassName(String className) { this.className = className; return this; } public String getJsonObject() { return jsonObject; } public SerializerObject setJsonObject(String jsonObject) { this.jsonObject = jsonObject; return this; } @Override public String toString() { return JSON.toJSONString(this); } } }
然后我们定义一个RedisConfig,将设置这个序列化对象:
package love.xiaohh.cost.configurations; import love.xiaohh.cost.constants.Constants; import love.xiaohh.cost.utils.storage.RedisJsonSerializerImpl; 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.StringRedisSerializer; @Configuration public class RedisConfig { @Bean(Constants.REDISTEMPLATE) public RedisTemplateredisTemplate(RedisConnectionFactory redisConnectionFactory) { // 缓存 *** 作对象 RedisTemplate redisTemplate = new RedisTemplate (); // 设置链接工厂 redisTemplate.setConnectionFactory(redisConnectionFactory); // 键的序列化器 redisTemplate.setKeySerializer(new StringRedisSerializer()); // 值的序列化器,这里我们用的是我们自己配置好的 redisTemplate.setValueSerializer(new RedisJsonSerializerImpl<>()); return redisTemplate; } }
其中key的序列化器使用自带的 StringRedisSerializer,然后value序列化使用我们自定义的 RedisJsonSerializerImpl,这个类就定义好了,我们运行看看效果:
可以发现key和value的可观测性提高了许多,好了下课
欢迎分享,转载请注明来源:内存溢出
评论列表(0条)