国产 无码 综合区,色欲AV无码国产永久播放,无码天堂亚洲国产AV,国产日韩欧美女同一区二区

【Redis】Redis 的學習教程(五)之 SpringBoot 集成 Redis

這篇具有很好參考價值的文章主要介紹了【Redis】Redis 的學習教程(五)之 SpringBoot 集成 Redis。希望對大家有所幫助。如果存在錯誤或未考慮完全的地方,請大家不吝賜教,您也可以點擊"舉報違法"按鈕提交疑問。

在前幾篇文章中,我們詳細介紹了 Redis 的一些功能特性以及主流的 java 客戶端 api 使用方法。

在當前流行的微服務以及分布式集群環(huán)境下,Redis 的使用場景可以說非常的廣泛,能解決集群環(huán)境下系統(tǒng)中遇到的不少技術(shù)問題,在此列舉幾個使用 Redis 經(jīng)常用到的功能:

  • 分布式緩存:在分布式的集群架構(gòu)中,將緩存存儲在內(nèi)存中會出現(xiàn)很多的問題,比如用戶回話信息,因為這部分信息需要與其他機器共享,此時利用 Redis 可以很好的解決機器之間數(shù)據(jù)共享的問題,緩存也是 Redis 中使用最多的場景
  • 分布式鎖:在高并發(fā)的情況下,我們需要一個鎖來防止并發(fā)帶來的臟數(shù)據(jù),Java 自帶的鎖機制顯然對進程間的并發(fā)并不好使,此時利用 Redis 的單線程特性,實現(xiàn)分布式鎖控制
  • 接口限流:在集群環(huán)境下,可以利用 Redis 的分布式自增 ID 功能,精準的統(tǒng)計每個接口在指定時間內(nèi)的請求次數(shù),利用這個特性,可以定向限制某個接口惡意頻刷

當然 Redis 的使用場景并不僅僅只有這么多,還有很多未列出的場景,如發(fā)布/訂閱,分布鎖集合等。

現(xiàn)實中我們大部分的微服務項目,都是基于 SpringBoot 框架進行快速開發(fā),在 SpringBoot 項目中我們應該如何使用 Redis 呢?代碼實踐如下。

1. 開發(fā)環(huán)境

  • IDEA:2021.3.3
  • JDK:1.8
  • SpringBoot:2.7.14
  • Maven:3.6.3

咱們通過程序是不能直接連接 Redis,得利用客戶端工具才能進行連接。比較常用的有兩種:Jedis、Lettuce。

在 springboot 1.5.x 版本的默認的 Redis 客戶端是 Jedis 實現(xiàn)的,springboot 2.x 版本中默認客戶端是用 lettuce實現(xiàn)的。

既然 LettuceJedis 的都是連接 Redis 的客戶端,那么它們有什么區(qū)別呢?

  • Jedis 在實現(xiàn)上是直連 Redis Server,多線程環(huán)境下非線程安全,除非使用連接池,為每個 Redis 實例增加 物理連接
  • Lettuce 是 一種可伸縮,線程安全,完全非阻塞的Redis客戶端,多個線程可以共享一個 RedisConnection,它利用 Netty NIO 框架來高效地管理多個連接,從而提供了異步和同步數(shù)據(jù)訪問方式,用于構(gòu)建非阻塞的反應性應用程序

2. 代碼實戰(zhàn)

在 SpringBoot 集成的 Redis 時,我這里采用的是 Lettuce

2.1 默認使用 Lettuce

1、引入依賴:

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

2、添加配置:

spring:
  redis:
    host: localhost
    port: 6379
    password:
    timeout: 2000s
    # 配置文件中添加 lettuce.pool 相關(guān)配置,則會使用到lettuce連接池
    lettuce:
      pool:
        max-active: 8  # 連接池最大連接數(shù)(使用負值表示沒有限制) 默認為8
        max-wait: -1ms # 接池最大阻塞等待時間(使用負值表示沒有限制) 默認為-1ms
        max-idle: 8    # 連接池中的最大空閑連接 默認為8
        min-idle: 0    # 連接池中的最小空閑連接 默認為 0

2.2 換成 Jedis

<dependency>
    <groupId>org.springframework.boot</groupId>
    <artifactId>spring-boot-starter-data-redis</artifactId>
    <exclusions>
        <exclusion>
            <groupId>io.lettuce</groupId>
            <artifactId>lettuce-core</artifactId>
        </exclusion>
    </exclusions>
</dependency>
<dependency>
    <groupId>redis.clients</groupId>
    <artifactId>jedis</artifactId>
</dependency>

jedis 中會引入 commons-pool2 依賴,如果沒有引入:

<dependency>
    <groupId>org.apache.commons</groupId>
    <artifactId>commons-pool2</artifactId>
</dependency>

添加配置:

spring:
  redis:
    host: localhost
    port: 6379
    password:
    timeout: 2000s
    # 配置文件中添加 jedis.pool 相關(guān)配置,則會使用到 jedis 連接池
    jedis:
      pool:
        max-active: 10
        max-idle: 8
        min-idle: 0
        max-wait: 60s

2.3 使用 RedisTemplate 對象操作 Redis

在 SpringBoot 中,是使用 RedisTemplate 對象來操作 Redis 的。

在 Springboot 自動配置原理中,涉及到以下兩方面:

  1. SpringBoot 中所有的配置類,都有一個自動配置類。RedisAutoConfiguration
  2. 自動配置類都會綁定一個配置文件 properties。RedisProperties

RedisAutoConfiguration.class

public class RedisAutoConfiguration {
    public RedisAutoConfiguration() {
    }

    @Bean
    @ConditionalOnMissingBean(name = {"redisTemplate"})
    @ConditionalOnSingleCandidate(RedisConnectionFactory.class)
    public RedisTemplate<Object, Object> redisTemplate(RedisConnectionFactory redisConnectionFactory) {
        RedisTemplate<Object, Object> template = new RedisTemplate();
        template.setConnectionFactory(redisConnectionFactory);
        return template;
    }

    @Bean
    @ConditionalOnMissingBean
    @ConditionalOnSingleCandidate(RedisConnectionFactory.class)
    public StringRedisTemplate stringRedisTemplate(RedisConnectionFactory redisConnectionFactory) {
        return new StringRedisTemplate(redisConnectionFactory);
    }
}

StringRedisTemplate

public class StringRedisTemplate extends RedisTemplate<String, String> {
    public StringRedisTemplate() {
        this.setKeySerializer(RedisSerializer.string());
        this.setValueSerializer(RedisSerializer.string());
        this.setHashKeySerializer(RedisSerializer.string());
        this.setHashValueSerializer(RedisSerializer.string());
    }

    public StringRedisTemplate(RedisConnectionFactory connectionFactory) {
        this();
        this.setConnectionFactory(connectionFactory);
        this.afterPropertiesSet();
    }

    protected RedisConnection preProcessConnection(RedisConnection connection, boolean existingConnection) {
        return new DefaultStringRedisConnection(connection);
    }
}

通過上述看,注入了兩個類型的 RedisTemplate 對象:

  1. 如果沒有注入名稱為 redisTemplate 的 RedisTemplate 對象,則注入 RedisTemplate<Object, Object> 對象
  2. 注入 StringRedisTemplate 對象。而 StringRedisTemplate 對象又是繼承 RedisTemplate<String, String> 類的

使用上面兩個類型 RedisTemplate 的對象操作 Redis:

@RestController
@RequestMapping("/redis")
public class RedisController {

    @Autowired
    private StringRedisTemplate stringRedisTemplate;

    @Autowired
    private RedisTemplate<Object, Object> redisTemplate;

    @GetMapping("/set")
    public String set() {
        stringRedisTemplate.opsForValue().set("name", "zzc");
        redisTemplate.opsForValue().set("age", "zzc");
        return "set";
    }
}

調(diào)用成功后,我們使用 Redis 客戶端工具進行查看:

【Redis】Redis 的學習教程(五)之 SpringBoot 集成 Redis,中間件,SpringBoot,redis,學習,spring boot
發(fā)現(xiàn):

redisTemplate.opsForValue().set("age", "zzc"); 操作的 key、value 都變成亂碼。

springboot系列——redisTemplate和stringRedisTemplate對比、redisTemplate幾種序列化方式比較

通過 debug 源代碼知:RedisTemplate<Object, Object> 的 key、value 序列化默認都是 JdkSerializationRedisSerializer,序列化方法如下:

default byte[] serializeToByteArray(T object) throws IOException {
   ByteArrayOutputStream out = new ByteArrayOutputStream(1024);
   this.serialize(object, out);
   return out.toByteArray();
}

public void serialize(Object object, OutputStream outputStream) throws IOException {
    if (!(object instanceof Serializable)) {
        throw new IllegalArgumentException(this.getClass().getSimpleName() + " requires a Serializable payload but received an object of type [" + object.getClass().getName() + "]");
    } else {
        ObjectOutputStream objectOutputStream = new ObjectOutputStream(outputStream);
        objectOutputStream.writeObject(object);
        objectOutputStream.flush();
    }
}

將 key、value 進行序列化成 byte 類型,所以,看上去會亂碼。(可讀性差)

StringRedisTemplate 對象使用 RedisSerializer 序列的

2.4 自定義 RedisTemplate 對象

為了可讀性,可以使用 StringRedisTemplate 類,但有一個要求:key、value 都要求是 String 類型。

但這就有一個問題,我們平時用得對象比較多,那又如何存儲對象呢?

例如,我們這里的 User 對象:

public class User {
    private String id;
    private String userName;
    private Integer age;
    // getter/setter
}

由于 RedisTemplate<String, String> 的泛型參數(shù)都是 String 類型的,那我們只需要將 Java 對象轉(zhuǎn)換為 String 對象即可:

@Override
public boolean addUser(User user) {
   redisTemplate.opsForValue().set("user", JSON.toJSONString(user));
   String strUser = redisTemplate.opsForValue().get("user1");
   User resultUser = JSON.parseObject(strUser, User.class);
   return true;
}

存 Redis 之前,將 Java 對象轉(zhuǎn)換為 Json 字符串;讀取后,將 Json 字符串轉(zhuǎn)換為 Java 對象。

這樣做確實可行,但是,如果要存儲的對象較多的話,那豈不是要重復地將 Java 對象轉(zhuǎn)換為 Json 字符串?這樣是不是很繁瑣?

繼續(xù)看 RedisAutoConfiguration.class 源碼,發(fā)現(xiàn)被注入的 RedisTemplate<Object, Object>@ConditionalOnMissingBean(name="redisTemplate") 注解修飾:如果 Spring 容器中有了 RedisTemplate 對象了,這個自動配置的 RedisTemplate 不會實例化。因此我們可以直接自己寫個配置類,配置 RedisTemplate。并且,我們更希望 key 是 String 類型,value 是 Object 類型(String、int、對象等類型):

@Configuration
public class RedisConfig {

    @Bean
    public RedisTemplate<String, Object> redisTemplate(RedisConnectionFactory redisConnectionFactory) {
        RedisTemplate<String, Object> template = new RedisTemplate<>();
        template.setConnectionFactory(redisConnectionFactory);

        ObjectMapper om = new ObjectMapper();
        om.setVisibility(PropertyAccessor.ALL, JsonAutoDetect.Visibility.ANY);
        om.enableDefaultTyping(ObjectMapper.DefaultTyping.NON_FINAL);
        // json 序列化配置
        Jackson2JsonRedisSerializer<Object> jackson2JsonRedisSerializer = new Jackson2JsonRedisSerializer<>(Object.class);
        jackson2JsonRedisSerializer.setObjectMapper(om);
        // String 序列化
        StringRedisSerializer stringRedisSerializer = new StringRedisSerializer();
        // 所有的 key 采用 string 的序列化
        template.setKeySerializer(stringRedisSerializer);
        // 所有的 value 采用 jackson 的序列化
        template.setValueSerializer(jackson2JsonRedisSerializer);
        // hash 的 key 采用 string 的序列化
        template.setHashKeySerializer(stringRedisSerializer);
        // hash 的 value 采用 jackson 的序列化
        template.setHashValueSerializer(jackson2JsonRedisSerializer);
        template.afterPropertiesSet();
        return template;
    }
}

測試:文章來源地址http://www.zghlxwxcb.cn/news/detail-655357.html

@RestController
@RequestMapping("/redis")
public class RedisController {

    @Autowired
    private RedisTemplate<String, Object> redisTemplate;

    @GetMapping("/set")
    public String set() {
        User user = new User();
        user.setName("zzc");
        user.setAge(18);
        redisTemplate.opsForValue().set("user", user);
        return "set";
    }

}

2.5 RedisUtil 工具類

@Component
public class RedisUtil {

    @Autowired
    private RedisTemplate<String, Object> redisTemplate;


    // ============================Common=============================
    
    public void setHashValueSerializer(RedisSerializer serializer) {
        redisTemplate.setHashValueSerializer(serializer);
    }

    /**
     * 指定緩存失效時間
     *
     * @author zzc
     * @date 2023/8/2 11:06
     * @param key    鍵
     * @param time   時間(秒)
     * @return boolean
     */
    public boolean expire(String key, long time) {
        try {
            if (time > 0) {
                redisTemplate.expire(key, time, TimeUnit.SECONDS);
            }
            return true;
        } catch (Exception e) {
            e.printStackTrace();
            return false;
        }
    }

    /**
     * 根據(jù)key 獲取過期時間
     *
     * @author zzc
     * @date 2023/8/2 11:07
     * @param key    鍵 不能為null
     * @return long  時間(秒) 返回0代表為永久有效
     */
    public Long getExpire(String key) {
        return redisTemplate.getExpire(key, TimeUnit.SECONDS);
    }

    /**
     * 判斷key是否存在
     *
     * @author zzc
     * @date 2023/8/2 11:07
     * @param key      鍵
     * @return boolean 存在 false不存在
     */
    public boolean hasKey(String key) {
        try {
            return Boolean.TRUE.equals(redisTemplate.hasKey(key));
        } catch (Exception e) {
            e.printStackTrace();
            return false;
        }
    }

    /**
     * 刪除緩存
     *
     * @author zzc
     * @date 2023/8/2 11:08
     * @param key   可以傳一個值 或多個
     */
    @SuppressWarnings("unchecked")
    public void del(String... key) {
        if (key != null && key.length > 0) {
            if (key.length == 1) {
                redisTemplate.delete(key[0]);
            } else {
                //springboot2.4后用法
                redisTemplate.delete(Arrays.asList(key));
            }
        }
    }

    /**
     * 獲取指定前綴的一系列key
     * 使用scan命令代替keys, Redis是單線程處理,keys命令在KEY數(shù)量較多時,
     * 操作效率極低【時間復雜度為O(N)】,該命令一旦執(zhí)行會嚴重阻塞線上其它命令的正常請求
     *
     * @author zzc
     * @date 2023/8/2 11:53
     * @param keyPrefix
     * @return java.util.Set<java.lang.String>
     */
    public Set<String> keys(String keyPrefix) {
        String realKey = keyPrefix + "*";
        try {
            return redisTemplate.execute((RedisCallback<Set<String>>) connection -> {
                Set<String> binaryKeys = new HashSet<>();
                //springboot2.4后用法
                Cursor<byte[]> cursor = connection.scan(ScanOptions.scanOptions().match(realKey).count(Integer.MAX_VALUE).build());
                while (cursor.hasNext()) {
                    binaryKeys.add(new String(cursor.next()));
                }

                return binaryKeys;
            });
        } catch (Throwable e) {
            e.printStackTrace();
        }
        return null;
    }

    /**
     * 刪除指定前綴的一系列key
     *
     * @author zzc
     * @date 2023/8/2 11:53
     * @param keyPrefix
     */
    public void removeAll(String keyPrefix) {
        try {
            Set<String> keys = keys(keyPrefix);
            redisTemplate.delete(keys);
        } catch (Throwable e) {
            e.printStackTrace();
        }
    }
    
    // 執(zhí)行 lua 腳本
    public <T> T execute(RedisScript<T> script, List<String> keys, Object... args) {
        return redisTemplate.execute(script, keys, args);
    }

    public boolean convertAndSend(String channel, Object message) {
        if (!StringUtils.hasText(channel)) {
            return false;
        }
        try {
            redisTemplate.convertAndSend(channel, message);
            return true;
        } catch (Exception e) {
            e.printStackTrace();
        }
        return false;
    }


    // ============================String=============================

    /**
     * 普通緩存獲取
     *
     * @author zzc
     * @date 2023/8/2 11:08
     * @param key                   鍵
     * @return java.lang.Object     值
     */
    public Object get(String key) {
        return key == null ? null : redisTemplate.opsForValue().get(key);
    }

    /**
     * 普通緩存放入
     * @author zzc
     * @date 2023/8/2 11:09
     * @param key           鍵
     * @param value         值
     * @return boolean      true成功 false失敗
     */
    public boolean set(String key, Object value) {
        try {
            redisTemplate.opsForValue().set(key, value);
            return true;
        } catch (Exception e) {
            e.printStackTrace();
            return false;
        }
    }

    /**
     * 普通緩存放入并設置過期時間
     *
     * @author zzc
     * @date 2023/8/2 11:09
     * @param key     鍵
     * @param value   值
     * @param time    時間(秒) time要大于0 如果time小于等于0 將設置無限期
     * @return boolean  true成功 false 失敗
     */
    public boolean set(String key, Object value, long time) {
        try {
            if (time > 0) {
                redisTemplate.opsForValue().set(key, value, time, TimeUnit.SECONDS);
            } else {
                set(key, value);
            }
            return true;
        } catch (Exception e) {
            e.printStackTrace();
            return false;
        }
    }

    /**
     * 遞增
     * @author zzc
     * @date 2023/8/2 11:10
     * @param key         鍵
     * @param delta       要增加幾(大于0)
     * @return java.lang.Long
     */
    public Long incr(String key, long delta) {
        if (delta < 0) {
            throw new RuntimeException("遞增因子必須大于0");
        }
        return redisTemplate.opsForValue().increment(key, delta);
    }

    /**
     * 遞減
     *
     * @author zzc
     * @date 2023/8/2 11:11
     * @param key                 鍵
     * @param delta               要減少幾(小于0)
     * @return java.lang.Long
     */
    public Long decr(String key, long delta) {
        if (delta < 0) {
            throw new RuntimeException("遞減因子必須大于0");
        }
        return redisTemplate.opsForValue().increment(key, -delta);
    }

    public boolean setNx(String key, Object value) {
        return Boolean.TRUE.equals(redisTemplate.opsForValue().setIfAbsent(key, value));
    }
    
    public boolean setNx(String key, Object value, long time) {
        return Boolean.TRUE.equals(redisTemplate.opsForValue().setIfAbsent(key, value, time, TimeUnit.SECONDS));
    }
    
    public void multiSet(Map<String, Object> map) {
        redisTemplate.opsForValue().multiSet(map);
    }

    public List<Object> multiGet(List<String> keys) {
        return redisTemplate.opsForValue().multiGet(keys);
    }


    // ================================Hash=================================

    /**
     * Hash Get
     * @author zzc
     * @date 2023/8/2 11:12
     * @param key                鍵 不能為null
     * @param item               項 不能為null
     * @return java.lang.Object
     */
    public Object hget(String key, String item) {
        return redisTemplate.opsForHash().get(key, item);
    }

    /**
     * 獲取Key對應的所有鍵值
     *
     * @author zzc
     * @date 2023/8/2 11:12
     * @param key                                                  鍵
     * @return java.util.Map<java.lang.Object,java.lang.Object>    對應的多個鍵值
     */
    public Map<Object, Object> hmget(String key) {
        return redisTemplate.opsForHash().entries(key);
    }

    /**
     * Hash Set
     *
     * @author zzc
     * @date 2023/8/2 11:13
     * @param key         鍵
     * @param map         對應多個鍵值
     * @return boolean    true 成功 false 失敗
     */
    public boolean hmset(String key, Map<String, Object> map) {
        try {
            redisTemplate.opsForHash().putAll(key, map);
            return true;
        } catch (Exception e) {
            e.printStackTrace();
            return false;
        }
    }

    /**
     * Hash Set 并設置過期時間
     * @author zzc
     * @date 2023/8/2 11:13
     * @param key        鍵
     * @param map        對應多個鍵值
     * @param time       時間(秒)
     * @return boolean   true成功 false失敗
     */
    public boolean hmset(String key, Map<String, Object> map, long time) {
        try {
            redisTemplate.opsForHash().putAll(key, map);
            if (time > 0) {
                expire(key, time);
            }
            return true;
        } catch (Exception e) {
            e.printStackTrace();
            return false;
        }
    }

    /**
     * 向一張hash表中放入數(shù)據(jù),如果不存在將創(chuàng)建
     *
     * @param key   鍵
     * @param item  項
     * @param value 值
     * @return true 成功 false失敗
     */
    public boolean hset(String key, String item, Object value) {
        try {
            redisTemplate.opsForHash().put(key, item, value);
            return true;
        } catch (Exception e) {
            e.printStackTrace();
            return false;
        }
    }

    /**
     * 向一張hash表中放入數(shù)據(jù),如果不存在將創(chuàng)建
     *
     * @param key   鍵
     * @param item  項
     * @param value 值
     * @param time  時間(秒) 注意:如果已存在的hash表有過期時間,這里將會替換原有的過期時間
     * @return true 成功 false失敗
     */
    public boolean hset(String key, String item, Object value, long time) {
        try {
            redisTemplate.opsForHash().put(key, item, value);
            if (time > 0) {
                expire(key, time);
            }
            return true;
        } catch (Exception e) {
            e.printStackTrace();
            return false;
        }
    }

    /**
     * 刪除hash表中的項
     *
     * @author zzc
     * @date 2023/8/2 11:38
     * @param key   鍵 不能為null
     * @param item  項 可以使多個 不能為null
     */
    public void hdel(String key, Object... item) {
        redisTemplate.opsForHash().delete(key, item);
    }

    /**
     * 判斷 hash 表中是否有該項的值
     *
     * @author zzc
     * @date 2023/8/2 11:38
     * @param key    鍵 不能為null
     * @param item   項 不能為null
     * @return boolean  true 存在 false不存在
     */
    public boolean hHasKey(String key, String item) {
        return redisTemplate.opsForHash().hasKey(key, item);
    }

    /**
     * hash 遞增 如果不存在,就會創(chuàng)建一個 并把新增后的值返回
     *
     * @author zzc
     * @date 2023/8/2 11:40
     * @param key    鍵
     * @param item   項
     * @param by     要增加幾(大于0)
     * @return double
     */
    public double hincr(String key, String item, double by) {
        return redisTemplate.opsForHash().increment(key, item, by);
    }

    public Long hincr(String key, String item, long by) {
        return redisTemplate.opsForHash().increment(key, item, by);
    }

    /**
     * hash 遞減
     *
     * @author zzc
     * @date 2023/8/2 11:40
     * @param key    鍵
     * @param item   項
     * @param by     要減少幾(小于0)
     * @return double
     */
    public double hdecr(String key, String item, double by) {
        return redisTemplate.opsForHash().increment(key, item, -by);
    }

    public List<Object> hmultiGet(String key, List<Object> items) {
        return redisTemplate.opsForHash().multiGet(key, items);
    }


    // ============================set=============================

    /**
     * 根據(jù)key獲取Set中的所有值
     *
     * @author zzc
     * @date 2023/8/2 11:41
     * @param key
     * @return java.util.Set<java.lang.Object>
     */
    public Set<Object> sGet(String key) {
        try {
            return redisTemplate.opsForSet().members(key);
        } catch (Exception e) {
            e.printStackTrace();
            return null;
        }
    }

    /**
     * 根據(jù)value從一個set中查詢,是否存在
     *
     * @author zzc
     * @date 2023/8/2 11:41
     * @param key       鍵
     * @param value     值
     * @return boolean  true 存在 false不存在
     */
    public boolean sHasKey(String key, Object value) {
        try {
            return Boolean.TRUE.equals(redisTemplate.opsForSet().isMember(key, value));
        } catch (Exception e) {
            e.printStackTrace();
            return false;
        }
    }

    /**
     * 將數(shù)據(jù)放入set緩存
     *
     * @author zzc
     * @date 2023/8/2 11:42
     * @param key       鍵
     * @param values    值 可以是多個
     * @return long     成功個數(shù)
     */
    public Long sSet(String key, Object... values) {
        try {
            return redisTemplate.opsForSet().add(key, values);
        } catch (Exception e) {
            e.printStackTrace();
            return 0L;
        }
    }

    /**
     * 將 set 數(shù)據(jù)放入緩存
     *
     * @author zzc
     * @date 2023/8/2 11:42
     * @param key     鍵
     * @param time    時間(秒)
     * @param values  值 可以是多個
     * @return long   成功個數(shù)
     */
    public Long sSetAndTime(String key, long time, Object... values) {
        try {
            Long count = redisTemplate.opsForSet().add(key, values);
            if (time > 0) {
                expire(key, time);
            }
            return count;
        } catch (Exception e) {
            e.printStackTrace();
            return 0L;
        }
    }

    /**
     * 獲取set緩存的長度
     *
     * @author zzc
     * @date 2023/8/2 11:45
     * @param key
     * @return long
     */
    public Long sGetSetSize(String key) {
        try {
            return redisTemplate.opsForSet().size(key);
        } catch (Exception e) {
            e.printStackTrace();
            return 0L;
        }
    }

    /**
     * 移除值為value的
     *
     * @author zzc
     * @date 2023/8/2 11:45
     * @param key    鍵
     * @param values 值 可以是多個
     * @return long  移除的個數(shù)
     */
    public Long setRemove(String key, Object... values) {
        try {
            return redisTemplate.opsForSet().remove(key, values);
        } catch (Exception e) {
            e.printStackTrace();
            return 0L;
        }
    }


    // ===============================List=================================

    /**
     * 獲取list緩存的內(nèi)容
     *
     * @author zzc
     * @date 2023/8/2 11:46
     * @param key      鍵
     * @param start    開始
     * @param end      結(jié)束 0 到 -1代表所有值
     * @return java.util.List<java.lang.Object>
     */
    public List<Object> lGet(String key, long start, long end) {
        try {
            return redisTemplate.opsForList().range(key, start, end);
        } catch (Exception e) {
            e.printStackTrace();
            return null;
        }
    }

    /**
     * 獲取list緩存的長度
     *
     * @author zzc
     * @date 2023/8/2 11:47
     * @param key
     * @return long
     */
    public Long lGetListSize(String key) {
        try {
            return redisTemplate.opsForList().size(key);
        } catch (Exception e) {
            e.printStackTrace();
            return 0L;
        }
    }

    /**
     * 通過索引 獲取list中的值
     *
     * @author zzc
     * @date 2023/8/2 11:47
     * @param key     鍵
     * @param index   索引 index>=0時, 0 表頭,1 第二個元素,依次類推;index<0時,-1,表尾,-2倒數(shù)第二個元素,依次類推
     * @return java.lang.Object
     */
    public Object lGetIndex(String key, long index) {
        try {
            return redisTemplate.opsForList().index(key, index);
        } catch (Exception e) {
            e.printStackTrace();
            return null;
        }
    }

    /**
     * 將list放入緩存
     * @author zzc
     * @date 2023/8/2 11:48
     * @param key       鍵
     * @param value     值
     * @return boolean
     */
    public boolean lSet(String key, Object value) {
        try {
            redisTemplate.opsForList().rightPush(key, value);
            return true;
        } catch (Exception e) {
            e.printStackTrace();
            return false;
        }
    }

    /**
     * 將list放入緩存
     * @author zzc
     * @date 2023/8/2 11:48
     * @param key       鍵
     * @param value     值
     * @param time  時間(秒)
     * @return boolean
     */
    public boolean lSet(String key, Object value, long time) {
        try {
            redisTemplate.opsForList().rightPush(key, value);
            if (time > 0) {
                expire(key, time);
            }
            return true;
        } catch (Exception e) {
            e.printStackTrace();
            return false;
        }
    }

    /**
     * 將list放入緩存
     *
     * @author zzc
     * @date 2023/8/2 11:49
     * @param key        鍵
     * @param value      值
     * @return boolean   時間(秒)
     */
    public boolean lSet(String key, List<Object> value) {
        try {
            redisTemplate.opsForList().rightPushAll(key, value);
            return true;
        } catch (Exception e) {
            e.printStackTrace();
            return false;
        }
    }

    /**
     * 將list放入緩存
     *
     * @author zzc
     * @date 2023/8/2 11:49
     * @param key        鍵
     * @param value      值
     * @param time       時間(秒)
     * @return boolean
     */
    public boolean lSet(String key, List<Object> value, long time) {
        try {
            redisTemplate.opsForList().rightPushAll(key, value);
            if (time > 0) {
                expire(key, time);
            }
            return true;
        } catch (Exception e) {
            e.printStackTrace();
            return false;
        }
    }

    /**
     * 根據(jù)索引修改list中的某條數(shù)據(jù)
     *
     * @author zzc
     * @date 2023/8/2 11:51
     * @param key     鍵
     * @param index   索引
     * @param value   值
     * @return boolean
     */
    public boolean lUpdateIndex(String key, long index, Object value) {
        try {
            redisTemplate.opsForList().set(key, index, value);
            return true;
        } catch (Exception e) {
            e.printStackTrace();
            return false;
        }
    }

    /**
     * 移除N個值為value
     *
     * @author zzc
     * @date 2023/8/2 11:51
     * @param key    鍵
     * @param count  移除多少個
     * @param value  值
     * @return long  移除的個數(shù)
     */
    public Long lRemove(String key, long count, Object value) {
        try {
            return redisTemplate.opsForList().remove(key, count, value);
        } catch (Exception e) {
            e.printStackTrace();
            return 0L;
        }
    }

}

到了這里,關(guān)于【Redis】Redis 的學習教程(五)之 SpringBoot 集成 Redis的文章就介紹完了。如果您還想了解更多內(nèi)容,請在右上角搜索TOY模板網(wǎng)以前的文章或繼續(xù)瀏覽下面的相關(guān)文章,希望大家以后多多支持TOY模板網(wǎng)!

本文來自互聯(lián)網(wǎng)用戶投稿,該文觀點僅代表作者本人,不代表本站立場。本站僅提供信息存儲空間服務,不擁有所有權(quán),不承擔相關(guān)法律責任。如若轉(zhuǎn)載,請注明出處: 如若內(nèi)容造成侵權(quán)/違法違規(guī)/事實不符,請點擊違法舉報進行投訴反饋,一經(jīng)查實,立即刪除!

領支付寶紅包贊助服務器費用

相關(guān)文章

  • 【Redis】Redis 的學習教程(一)入門基礎

    【Redis】Redis 的學習教程(一)入門基礎

    Redis 全稱: Remote Dictionary Server(遠程字典服務器) ,是一款開源的,遵守 BSD 協(xié)議,使用 C 語言開發(fā)的 key-value 存儲系統(tǒng)。簡單的說,它是一款跨平臺的非關(guān)系型數(shù)據(jù)庫,支持優(yōu)先內(nèi)存存儲, 并提供多種語言的 API 客戶端 雖然開源軟件市場上也有很多優(yōu)秀的緩存服務中間件,

    2024年02月12日
    瀏覽(31)
  • 【Redis】Redis 的學習教程(十二)之在 Redis使用 lua 腳本

    lua 菜鳥教程:https://www.runoob.com/lua/lua-tutorial.html 在 Redis 使用 lua 腳本的好處: 減少網(wǎng)絡開銷 ??梢詫⒍鄠€請求通過腳本的形式一次發(fā)送,減少網(wǎng)絡時延及開銷 原子性操作 。Redis會將整個腳本作為一個整體執(zhí)行,中間不會被其他請求插入。因此在腳本運行過程中無需擔心會出

    2024年02月07日
    瀏覽(23)
  • 使用Spring Boot集成中間件:基礎篇

    在現(xiàn)代應用開發(fā)中,中間件在構(gòu)建高效、可擴展的系統(tǒng)方面起著至關(guān)重要的作用。而Spring Boot作為一種快速開發(fā)框架,提供了豐富的集成中間件的能力,使得我們能夠輕松地將各種中間件引入到我們的應用程序中。本文將重點介紹如何使用Spring Boot集成Redis中間件,并提供一個

    2024年01月25日
    瀏覽(23)
  • 中間件redis的使用

    Java中的中間件配置體現(xiàn)在springboot的yml配置文件中。Springboot框架支持微服務和中間件和restful api遠程服務的調(diào)用。中間件是Java web系統(tǒng)的中間層的服務系統(tǒng)的調(diào)用接口。Springboot的自動裝配和約定大于配置機制初始化springcontext的容器空間和注冊組件。使用容器管理服務注冊對象

    2024年02月05日
    瀏覽(23)
  • 01.Redis中間件實戰(zhàn)1

    字符串 需求:將用戶信息存儲至緩存中,實現(xiàn)每次前端請求獲取用戶個人詳情時直接從緩存中獲取。來演示字符串的寫入與讀取。 技術(shù)方案:為了實現(xiàn)這個需求,首先需要建立用戶對象實體,里面包含用戶個人的各種信息,包括ID、年齡、姓名、用戶名及住址等, 然后采用

    2024年02月20日
    瀏覽(24)
  • 中間件: Redis安裝與部署

    集群部署 啟動6個redis節(jié)點 擴縮容 https://blog.csdn.net/lzb348110175/article/details/122168638 擴容: 添加兩個節(jié)點, 第一個節(jié)點表示新節(jié)點,第二個節(jié)點表示集群中已有的任意一個節(jié)點 分配slot, 后面的節(jié)點是已有的節(jié)點 添加slave, 第一個為slave, 第二個為slave對應的master 縮容: 查看集

    2024年02月12日
    瀏覽(22)
  • 緩存中間件Redis必知必會

    作者: 逍遙Sean 簡介:一個主修Java的Web網(wǎng)站游戲服務器后端開發(fā)者 主頁:https://blog.csdn.net/Ureliable 覺得博主文章不錯的話,可以三連支持一下~ 如有需要我的支持,請私信或評論留言! 前言: 本文是對redis的基本用法操作的整理。 如果需要在linux環(huán)境中搭建一個redis服務參考

    2024年02月11日
    瀏覽(17)
  • 【Redis學習筆記01】快速入門(含安裝教程)

    【Redis學習筆記01】快速入門(含安裝教程)

    先來看門見山的給出 Redis 的概念: Redis:是一種基于內(nèi)存的高性能K-V鍵值型NoSQL數(shù)據(jù)庫 Redis官網(wǎng):https://redis.io/ 1.1 初識NoSQL 想必大家都對關(guān)系型數(shù)據(jù)庫更為熟悉!如MySQL、Oracle、SQL Server都是比較常見的關(guān)系型數(shù)據(jù)庫,所謂關(guān)系型數(shù)據(jù)庫主要以二維表作為數(shù)據(jù)結(jié)構(gòu)進行存儲,但

    2024年01月22日
    瀏覽(56)
  • Go重寫Redis中間件 - Go實現(xiàn)Redis集群

    Go重寫Redis中間件 - Go實現(xiàn)Redis集群

    這章的內(nèi)容是將我們之前實現(xiàn)的單機版的Redis擴充成集群版,給Redis增加集群功能,在增加集群功能之前,我們先學習一下在分布式系統(tǒng)中引用非常廣泛的技術(shù)一致性哈希,一致性哈希在我們項目里就應用在我們Redis集群的搭建這塊 詳解一致性哈希 Redis集群需求背景 單臺服務

    2024年02月13日
    瀏覽(30)
  • 使用Spring Boot集成中間件:Elasticsearch基礎->提高篇

    Elasticsearch是一個開源的分布式搜索和分析引擎,廣泛用于構(gòu)建實時的搜索和分析應用。在本篇博客中,我們將深入講解如何使用Spring Boot集成Elasticsearch,實現(xiàn)數(shù)據(jù)的索引、搜索和分析。 在開始之前,確保已經(jīng)完成以下準備工作: 安裝并啟動Elasticsearch集群 創(chuàng)建Elasticsearch索引

    2024年01月19日
    瀏覽(58)

覺得文章有用就打賞一下文章作者

支付寶掃一掃打賞

博客贊助

微信掃一掃打賞

請作者喝杯咖啡吧~博客贊助

支付寶掃一掃領取紅包,優(yōu)惠每天領

二維碼1

領取紅包

二維碼2

領紅包