美文网首页
SpringBoot-Redis

SpringBoot-Redis

作者: 张明学 | 来源:发表于2020-09-29 09:12 被阅读0次

    SpringBoot已经开发对Reids的自动配置(org.springframework.boot.autoconfigure.data.redis.RedisAutoConfiguration),只需要添加依赖包和配置信息即可完成集中。

    依赖配置

    <dependency>
        <groupId>org.springframework.boot</groupId>
        <artifactId>spring-boot-starter-data-redis</artifactId>
    </dependency>
    

    SpringBoot与Redis的集成配置

    配置信息

    配置属性类:org.springframework.boot.autoconfigure.data.redis.RedisProperties

    基础配置
    # Redis服务器地址
    spring.redis.host = ip
    # Redis服务器连接端口
    spring.redis.port = xxxx
    # Redis服务器连接密码(默认为空)
    spring.redis.password = xxxx
    # Redis数据库索引(默认为0)
    spring.redis.database = 0
    # 连接超时时间(毫秒)
    spring.redis.timeout = 10000
    
    Redis连接池配置

    在1.3.2以前版本的配置是:

    # 连接池最大连接数(使用负值表示没有限制)
    #spring.redis.pool.max-active = -1
    # 连接池最大阻塞等待时间(使用负值表示没有限制)
    #spring.redis.pool.max-wait = -1
    # 连接池中的最大空闲连接
    #spring.redis.pool.max-idle = 10
    # 连接池中的最小空闲连接
    #spring.redis.pool.min-idle = 5
    

    在2.x.x以上的版本提供了两个Redis客户端,分别是Jedis和Lettuce(SpringBoot2.0默认方式)。
    Jedis是Redis官方推荐的Java连接开发工具,是直连模式,在多个线程间共享一个Jedis实例时是线程不安全的,可以通过创建多个Jedis实例来解决,但当连接数量增多时,物理连接成本就较高同时会影响性能,因此较好的解决方法是使用JedisPool。
    Lettuce是一个可伸缩线程安全的Redis客户端。多个线程可以共享同一个RedisConnection。它利用优秀netty NIO框架来高效地管理多个连接。

    对象池依赖
    <dependency>
        <groupId>org.apache.commons</groupId>
        <artifactId>commons-pool2</artifactId>
    </dependency>
    
    Jedis客户端的连接池配置
    <dependency>
        <groupId>redis.clients</groupId>
        <artifactId>jedis</artifactId>
    </dependency>
    
    Lettuce客户端的连接池配置

    spring-boot-starter-data-redis中默认已经引用了,不需要添加额外的依赖

    配置

    # 连接池最大阻塞等待时间(使用负值表示没有限制)
    spring.redis.lettuce.pool.max-wait=-1
    # 连接池最大连接数
    spring.redis.lettuce.pool.max-active=-1
    # 连接池中的最大空闲连接
    spring.redis.lettuce.pool.max-idle=10
    # 最小空闲连接数
    spring.redis.lettuce.pool.min-idle=5
    

    RedisTemplate

    RedisTemplate提供了对redis高度封装的一个工具类,在对redis操作时需要RedisConnection,Jedis和Lettuce分别对RedisConnection做了实现。如果你的项目同时添加了lettuce和jedis依赖包,默认是使用的Lettuce。

    RedisTemplate配置

    @Configuration
    @AutoConfigureAfter(RedisAutoConfiguration.class)
    public class RedisConfig {
    
        /**
         * 配置自定义redisTemplate
         *
         * @return
         */
        @Bean
        RedisTemplate<Object, Object> redisTemplate(RedisConnectionFactory redisConnectionFactory) {
    
            RedisTemplate<Object, Object> template = new RedisTemplate<>();
            //使用fastjson序列化,默认就JDK的序列化策略
            FastJsonRedisSerializer fastJsonRedisSerializer = new FastJsonRedisSerializer(Object.class);
            // value值的序列化采用fastJsonRedisSerializer
            template.setValueSerializer(fastJsonRedisSerializer);
            template.setHashValueSerializer(fastJsonRedisSerializer);
            // key的序列化采用StringRedisSerializer
            template.setKeySerializer(new StringRedisSerializer());
            template.setHashKeySerializer(new StringRedisSerializer());
            template.setConnectionFactory(redisConnectionFactory);
            return template;
        }
    }
    

    针对数据的“序列化/反序列化”,提供了多种可选择策略,JdkSerializationRedisSerializer:POJO对象的存取场景,使用JDK本身序列化机制。
    StringRedisSerializer:Key或者value为字符串的场景,根据指定的charset对数据的字节序列编码成string,是“new String(bytes, charset)”和“string.getBytes(charset)”的直接封装。是最轻量级和高效的策略。
    JacksonJsonRedisSerializer、FastJsonRedisSerializer是jackson-jsonf和astjson工具提供了javabean与json之间的转换能力,可以将pojo实例序列化成json格式存储在redis中,也可以将json格式的数据转换成pojo实例。

    常用的API

    @Autowired注入RedisTemplate

    @Autowired
    private RedisTemplate redisTemplate;
    
    • 删除单个或多个key: redisTemplate.delete(key);
    • 指定key的失效时间:redisTemplate.expire(key,time,TimeUnit.MINUTES);
    • 根据key获取过期时间:Long expire = redisTemplate.getExpire(key);
    • 判断key是否存在:redisTemplate.hasKey(key);
    • Object类型相关操作
    redisTemplate.boundValueOps("test:zmx").set("zmx");
    redisTemplate.boundValueOps("test:zmx").get();
    
    redisTemplate.opsForValue().set("test:zmx","zmx");
    redisTemplate.opsForValue().get("test:zmx");
    
    • Hash类型相关操作(如果设置了valueSerializer通过redisTemplate.opsForValue()获取的值都是JSONObject)
    @Test
    public void testHash() {
        redisTemplate.boundHashOps("test:hash:zmx1").put("k1","v1");
        String v1 = (String) redisTemplate.boundHashOps("test:hash:zmx1").get("k1");
    
        HashMap map = new HashMap();
        map.put("k1","v1");
        redisTemplate.opsForValue().set("test:hash:zmx2",map,30, TimeUnit.SECONDS);
        HashMap cashMap = (HashMap) redisTemplate.opsForValue().get("test:hash:zmx2");
    }
    
    • Set类型相关操作(redisTemplate.boundSetOps)
    @Test
    public void testSet() {
        redisTemplate.boundSetOps("test:set:zmx1").add("setv1","setv2");
        redisTemplate.boundSetOps("test:set:zmx1").expire(10, TimeUnit.SECONDS);
        Assert.assertNotNull(redisTemplate.boundSetOps("test:set:zmx1"));
    
        HashSet set = new HashSet();
        set.add("setv1");
        set.add("setv2");
        redisTemplate.opsForValue().set("test:set:zmx2", set, 30, TimeUnit.SECONDS);
        Assert.assertNotNull(redisTemplate.opsForValue().get("test:set:zmx2"));
    }
    
    • List类型相关操作(redisTemplate.boundListOps)
    @Test
    public void testList() {
        redisTemplate.boundListOps("test:list:zmx1").leftPush("left1");
        redisTemplate.boundListOps("test:list:zmx1").rightPush("right1");
        redisTemplate.boundListOps("test:list:zmx1").expire(10, TimeUnit.SECONDS);
        Assert.assertEquals(redisTemplate.boundListOps("test:list:zmx1").leftPop(),"left1");
    
        List list = new ArrayList();
        list.add("listvalue1");
        redisTemplate.opsForValue().set("test:list:zmx2", list, 30, TimeUnit.SECONDS);
        Assert.assertNotNull(redisTemplate.opsForValue().get("test:list:zmx2"));
    }
    
    • ZSet(排序Set)类型的相关操作(redisTemplate.boundZSetOps)
    @Test
    public void testZSet() {
        redisTemplate.boundZSetOps("test:zset:zmx1").add("value1",10);
        redisTemplate.boundZSetOps("test:zset:zmx1").add("value2",20);
        redisTemplate.boundZSetOps("test:zset:zmx1").expire(10, TimeUnit.SECONDS);
        // 分值在5到15之间的元素个数,1个
        Assert.assertTrue(redisTemplate.boundZSetOps("test:zset:zmx1").count(5, 15) == 1L);
        // 获取元素的score
        Assert.assertEquals(redisTemplate.boundZSetOps("test:zset:zmx1").score("value1"),new Double(10));
    }
    

    相关文章

      网友评论

          本文标题:SpringBoot-Redis

          本文链接:https://www.haomeiwen.com/subject/lxisuktx.html