自定义Redis序列化工具
為什么用戶需要自己創建一個redis配置類?
SpringBoot提供了對Redis的自動配置功能,在RedisAutoConfiguration類中默認為我們配置了客戶端連接(Lettuce和Jedis),以及數據操作模板(StringRedisTemplate和RedisTemplate),下列代碼有一個@ConditionalOnMissingBean和@Bean的注解,@ConditionalOnMissingBean注解判斷是否執行初始化代碼,即如果用戶已經創建了bean,則相關的初始化代碼不再執行。這導致了默認的是redisTemplate方法會被執行。
RedisTemplate是Spring提供用于操作redis數據庫的一個類。將數據存放到Redis中,以及數據讀取。這里必然涉及到數據的序列化和反序列化。RedisTemplate默認的系列化類是JdkSerializationRedisSerializer,用JdkSerializationRedisSerializer序列化的話,被序列化的對象必須實現Serializable接口。在存儲內容時,除了屬性的內容外還存了其它內容在里面,總長度長,且不容易閱讀。所以才需要創建一個redis的配置類覆蓋默認的序列化。我們要求是存儲的數據可以方便查看,也方便反系列化,方便讀取數據。
spring為我們提供了多種序列化方式,都在org.springframework.data.redis.serializer包下,常用的分別是:
- JdkSerializationRedisSerializer
- GenericJackson2JsonRedisSerializer
- StringRedisSerializer
- Jackson2JsonRedisSerializer
JacksonJsonRedisSerializer是spring提供的序列化工具,GenericJackson2JsonRedisSerializer是fastjson提供的json序列化工具,兩者都能把字符串序列化成json,但是后者會在json中加入 @class屬性,類的全路徑包名,方便反系列化。前者如果存放了List則在反系列化的時候如果沒指定TypeReference則會報錯java.util.LinkedHashMap cannot be cast to 。
兩者的具體區別如下:JacksonJsonRedisSerializer和GenericJackson2JsonRedisSerializer的區別
通過RedisSerializer接口實現自定義的redis的序列化工具
Springboot中除了對常用的關系型數據庫提供了優秀的自動化支持之外,對于很多nosql數據庫一樣提供了自動化配置的支持,包括:redis、MongoDB、elasticsearch、solr和Cassandra。
1、springboot對Redis的支持和使用
Spring Boot提供的數據訪問框架Spring Data Redis基于Jedis??梢酝ㄟ^如下方式來配制maven依賴
<dependency><groupId>org.springframework.boot</groupId><artifactId>spring-boot-starter-data-redis</artifactId> </dependency>可以在application.properties中加入Redis服務端的相關配置,也可以使用springboot的方式直接在application.yml文件中進行配置,本文采用在.yml文件中配置的方式實現:
以下是一個redis配置工具類實例,該實例中使用StringRedisSerializer設置key的序列化方式為字符串方式,使用自定義redis序列化類 FastJsonRedisSerializer設置value的序列化方式為json方式。
2、自定義redis序列化類:
import com.alibaba.fastjson.JSON; import com.alibaba.fastjson.serializer.SerializerFeature; import org.springframework.data.redis.serializer.RedisSerializer; import org.springframework.data.redis.serializer.SerializationException; import java.nio.charset.Charset;/*** 自定義redis序列化類FastJsonRedisSerializer* @author: liumengbing* @date: 2019/05/28 10:52**/ public class FastJsonRedisSerializer<T> implements RedisSerializer<T> {public static final Charset DEFAULT_CHARSET = Charset.forName("UTF-8");private Class<T> clazz;public FastJsonRedisSerializer(Class<T> clazz) {super();this.clazz = clazz;}@Overridepublic byte[] serialize(T t) throws SerializationException {if(t == null){return new byte[0];}return JSON.toJSONString(t, SerializerFeature.WriteClassName).getBytes(DEFAULT_CHARSET);}@Overridepublic T deserialize(byte[] bytes) throws SerializationException {if(bytes == null || bytes.length < 0){return null;}String string = new String(bytes,DEFAULT_CHARSET);return JSON.parseObject(string,clazz);} }3、Redis配置工具類:
package com.example.springboottest;import com.fasterxml.jackson.annotation.JsonAutoDetect; import com.fasterxml.jackson.annotation.PropertyAccessor; import com.fasterxml.jackson.databind.ObjectMapper; import org.springframework.beans.factory.annotation.Qualifier; import org.springframework.beans.factory.annotation.Value; import org.springframework.context.annotation.Bean; import org.springframework.context.annotation.Configuration; import org.springframework.context.annotation.Primary; import org.springframework.data.redis.connection.RedisPassword; import org.springframework.data.redis.connection.RedisStandaloneConfiguration; import org.springframework.data.redis.connection.jedis.JedisConnectionFactory; import org.springframework.data.redis.core.RedisTemplate; import org.springframework.data.redis.serializer.Jackson2JsonRedisSerializer; import org.springframework.data.redis.serializer.StringRedisSerializer;/*** redis配置工具類* @author: liumengbing* @date: 2019/04/11 10:53**/ @Configuration public class RedisConfig {@Value("${spring.redis.host}")String rhost;@Value("${spring.redis.port}")Integer rport;@Value("${spring.redis.database}")Integer rdatabase;@Value("${spring.redis.password}")String rpassword;@Bean@Primarypublic JedisConnectionFactory jedisConnectionFactory(){RedisStandaloneConfiguration redisStandaloneConfiguration = new RedisStandaloneConfiguration(rhost, rport);redisStandaloneConfiguration.setDatabase(rdatabase);redisStandaloneConfiguration.setPassword(RedisPassword.of(rpassword));JedisConnectionFactory jedisConnectionFactory = new JedisConnectionFactory(redisStandaloneConfiguration);jedisConnectionFactory.afterPropertiesSet();return jedisConnectionFactory;}@Bean@Primarypublic RedisTemplate redisTemplate(@Qualifier("jedisConnectionFactory")JedisConnectionFactory jedisConnectionFactory){RedisTemplate redisTemplate = new RedisTemplate();StringRedisSerializer stringRedisSerializer = new StringRedisSerializer();//設置序列化Key的實例化對象,Key的序列化始終是字符串方式redisTemplate.setKeySerializer(stringRedisSerializer);redisTemplate.setHashKeySerializer(stringRedisSerializer);FastJsonRedisSerializer<Object> fastJsonRedisSerializer = new FastJsonRedisSerializer<>(Object.class);//設置序列化Value的實例化對象redisTemplate.setValueSerializer(fastJsonRedisSerializer);redisTemplate.setHashValueSerializer(fastJsonRedisSerializer);redisTemplate.setConnectionFactory(jedisConnectionFactory);redisTemplate.afterPropertiesSet();return redisTemplate;} }引申:
為什么Spring redis中緩存的對象需要實現 Serializable 序列化接口
使用Spring Data Redis時,遇到的幾個問題
總結
以上是生活随笔為你收集整理的自定义Redis序列化工具的全部內容,希望文章能夠幫你解決所遇到的問題。
- 上一篇: 在springboot中使用spring
- 下一篇: 使用HttpMessageConvert