SpringBoot整合Redis实现几种自定义数据序列化存储方式-创新互联

JDK自带序列化方式

在Java中RedisTemplete提供了统一的API来操作Redis,比如插入一条String类型的数据,我可以用
redisTemplate.opsForValue().set("name", "美羊羊");
SpringDataRedis可以接收任何类型的对象并将其转成Redis可以处理的字节,观察这段代码中set()方法的形参列表,发现传进去的key与value都被当作了Java对象Object来处理
在这里插入图片描述
将对象转成字节,这一操作好像和序列化非常相似,看一眼RedisTemplete实现过程,发现针对传入的不同key-value都会有相应的序列化器来操作:
在这里插入图片描述
进去可以看到,在头部定义的几个RedisSerializer类型变量都是null,均需要指定并初始化。
一般按照向set方法里传参的方式则会直接走默认的JDK序列化:
通过一次Debug来简单分析一下
首先,传入的value通过serialize()被转换成了字节数组
在这里插入图片描述
在serialize()方法的内部,则是将value值传入内部的convert()方法
在这里插入图片描述
而在convert()方法的内部则是调用了JDK内部的序列化工具,以流的形式将对象完成序列化
在这里插入图片描述
强制步入serialize()方法后,发现底层就是调用了ObjectoutputStream()来将对象转换成字节写入到Redis中!
但是去查看Redis却发现写入的数据不是以Java端写入的类型存入,而是以序列化的形式存入,并且key与value均被序列化。
在这里插入图片描述
如果这样的话:1.可读性很差2.内存占用大

专注于为中小企业提供做网站、网站制作服务,电脑端+手机端+微信端的三站合一,更高效的管理,为中小企业站前免费做网站提供优质的服务。我们立足成都,凝聚了一批互联网行业人才,有力地推动了上1000家企业的稳健成长,帮助中小企业通过网站建设实现规模扩充和转变。自定义序列化方式

上述的方式不推荐使用,我们可以人为改变一下RedisTemplete的序列化方式,即封装一个方法,指定key与value序列化的方式,不去使用默认的JDK内部序列化方式
就像这样:

@Configuration
public class ConfigRedis {@Bean
    public RedisTemplateredisTemplate(RedisConnectionFactory connectionFactory) {// 创建RedisTemplate对象
        RedisTemplatetemplate = new RedisTemplate<>();
        // 设置连接工厂
        template.setConnectionFactory(connectionFactory);
        // 创建JSON序列化工具
        GenericJackson2JsonRedisSerializer jsonRedisSerializer =
                new GenericJackson2JsonRedisSerializer();
        // 设置Key的序列化
        template.setKeySerializer(RedisSerializer.string());
        //静态方法 string()
        template.setHashKeySerializer(RedisSerializer.string());
        // 设置Value的序列化
        template.setValueSerializer(jsonRedisSerializer);
        template.setHashValueSerializer(jsonRedisSerializer);
        // 返回
        return template;
    }

}

其实就是创建一个RedisTemplete实例,并指定四个默认的序列化方式
在这里插入图片描述
主要就是将key序列化成String类型,将Object序列化成JSON类型数据而不是字节
在这里插入图片描述
在这里插入图片描述
并且可以在获取库中的数据时自动反序列化:
User o = (User) redisTemplate.opsForValue().get("user:001");

按照这样的模式,以后根据需要想转换成什么样的序列化方式就可以转成什么样的方式了

最合理的字符串序列化方式

对于我们这些初学者,自动化的方式确实很香(数据量少的情况下),由于实现反序列化时为了知道对象的类型而存在的那串数据:"@class": "com.yu7daily.Pojo.User",乍一看没什么,一旦数据量增多则会占用大量的内存,所以上述方式还是不建议使用
在这里插入图片描述
为了节省内存空间,实际开发中并不会使用JSON序列化器来处理value,而是统一使用String序列化器,要求只能存储String类型的key和value。当需要存储Java对象时,手动完成对象的序列化和反序列化。SpringDataRedis提供了RedisTemplate的子类:StringRedisTemplate,它的key和value的序列化方式默认就是String方式
在这里插入图片描述
由于继承了RedisTemplate就不需要再次去定义,直接使用该子类的实例化对象即可:
在这里插入图片描述

就像这样:

@Autowired
    private StringRedisTemplate stringRedisTemplate;

    private static final ObjectMapper mapper = new ObjectMapper();  //JSON工具

    @Test
    void testSaveUser() throws JsonProcessingException {// 创建对象
        User user = new User("懒羊羊", 77);
        // 手动序列化
        String json = mapper.writeValueAsString(user);
        // 写入数据
        stringRedisTemplate.opsForValue().set("user:002", json);

        // 获取数据
        String jsonUser = stringRedisTemplate.opsForValue().get("user:002");
        // 手动反序列化
        User user2 = mapper.readValue(jsonUser, User.class);
        System.out.println("user002 = " + user2);
    }

运行测试类,存入对象数据后发现果然没有了“@class”数据
在这里插入图片描述

你是否还在寻找稳定的海外服务器提供商?创新互联www.cdcxhl.cn海外机房具备T级流量清洗系统配攻击溯源,准确流量调度确保服务器高可用性,企业级服务器适合批量采购,新人活动首月15元起,快前往官网查看详情吧


本文名称:SpringBoot整合Redis实现几种自定义数据序列化存储方式-创新互联
分享URL:http://ybzwz.com/article/dihjsh.html