欧美bbbwbbbw肥妇,免费乱码人妻系列日韩,一级黄片

Springboot使用Redis實(shí)現(xiàn)定時(shí)任務(wù)的三種方式

 更新時(shí)間:2025年06月25日 10:10:23   作者:weixin_43833540  
本文介紹了三種Redis定時(shí)任務(wù)實(shí)現(xiàn)方式,鍵空間通知,有序集合輪詢,分布式鎖,文中通過示例代碼介紹的非常詳細(xì),對(duì)大家的學(xué)習(xí)或者工作具有一定的參考學(xué)習(xí)價(jià)值,需要的朋友們下面隨著小編來一起學(xué)習(xí)學(xué)習(xí)吧

一、基于 Redis 鍵空間通知(適合精確延時(shí)任務(wù))

原理:利用 Redis 的鍵過期事件(EXPIRE)觸發(fā)任務(wù)執(zhí)行,通過監(jiān)聽 __keyevent@*__:expired 通道捕獲事件。
步驟

啟用 Redis 鍵空間通知(redis.conf 或運(yùn)行時(shí)配置):

CONFIG SET notify-keyspace-events Ex

Spring Boot 監(jiān)聽器實(shí)現(xiàn)

@Component
public class KeyExpiredListener extends KeyExpirationEventMessageListener {
    public KeyExpiredListener(RedisMessageListenerContainer listenerContainer) {
        super(listenerContainer);
    }

    @Override
    public void onMessage(Message message, byte[] pattern) {
        String expiredKey = new String(message.getBody());
        if (expiredKey.startsWith("task:")) { // 過濾業(yè)務(wù)鍵
            System.out.println("執(zhí)行任務(wù): " + expiredKey);
            // 例如:task:123 過期時(shí)執(zhí)行訂單超時(shí)邏輯
        }
    }
}

注冊(cè)監(jiān)聽器

@Configuration
public class RedisConfig {
    @Bean
    RedisMessageListenerContainer container(RedisConnectionFactory factory, 
                                           KeyExpiredListener listener) {
        RedisMessageListenerContainer container = new RedisMessageListenerContainer();
        container.setConnectionFactory(factory);
        container.addMessageListener(listener, new PatternTopic("__keyevent@*__:expired"));
        return container;
    }
}

調(diào)度任務(wù)(設(shè)置帶過期時(shí)間的鍵):

@Service
public class TaskScheduler {
    @Autowired
    private StringRedisTemplate redisTemplate;

    public void scheduleTask(String taskId, long delaySeconds) {
        redisTemplate.opsForValue().set("task:" + taskId, "data", 
                delaySeconds, TimeUnit.SECONDS); // 鍵在 delaySeconds 秒后過期
    }
}

注意:需在 Redis 配置中開啟 notify-keyspace-events Ex。

二、基于 Redis 有序集合輪詢(適合批量定時(shí)任務(wù))

原理:將任務(wù)執(zhí)行時(shí)間作為 ZSETscore,通過定時(shí)任務(wù)查詢到期的任務(wù)并執(zhí)行。
步驟

添加任務(wù)到 ZSET

public void addTask(String taskId, Instant executeTime) {
    stringRedisTemplate.opsForZSet().add("scheduled_tasks", taskId, 
          executeTime.getEpochSecond());
}

定時(shí)掃描并執(zhí)行任務(wù)(每分鐘輪詢):

@Scheduled(cron = "0 * * * * *") // 每分鐘執(zhí)行
public void pollTasks() {
    long now = Instant.now().getEpochSecond();
    Set<String> tasks = stringRedisTemplate.opsForZSet()
          .rangeByScore("scheduled_tasks", 0, now); // 獲取所有到期任務(wù)

    for (String task : tasks) {
        System.out.println("執(zhí)行任務(wù): " + task);
        // 執(zhí)行后移除任務(wù)
        stringRedisTemplate.opsForZSet().remove("scheduled_tasks", task);
    }
}

優(yōu)點(diǎn):避免鍵空間通知的丟失風(fēng)險(xiǎn),適合任務(wù)量大的場(chǎng)景。

三、基于 Redis 分布式鎖(防集群任務(wù)重復(fù)執(zhí)行)

原理:在分布式環(huán)境中,通過 Redis 鎖確保同一時(shí)間只有一個(gè)實(shí)例執(zhí)行定時(shí)任務(wù)。
代碼示例

@Component
public class DistributedTask {
    @Autowired
    private StringRedisTemplate redisTemplate;
    private static final String LOCK_KEY = "TASK_LOCK:ORDER_CLEAN";

    @Scheduled(cron = "0 0 3 * * ?") // 每天凌晨3點(diǎn)執(zhí)行
    public void dailyTask() {
        Boolean locked = redisTemplate.opsForValue()
                .setIfAbsent(LOCK_KEY, "locked", Duration.ofMinutes(10));
        if (Boolean.TRUE.equals(locked)) {
            try {
                cleanExpiredOrders(); // 執(zhí)行核心任務(wù)
            } finally {
                redisTemplate.delete(LOCK_KEY); // 釋放鎖(可選)
            }
        }
    }
}

關(guān)鍵點(diǎn)

  • 使用 setIfAbsent 原子操作獲取鎖,避免并發(fā)沖突。
  • 鎖自動(dòng)過期防止死鎖(如任務(wù)執(zhí)行超時(shí))。

??版本要求??:
??Spring Data Redis ≥ 2.3.0??:該版本引入了 setIfAbsent(key, value, duration) 方法,支持??原子性設(shè)置鍵值+過期時(shí)間??(對(duì)應(yīng) Redis 的 SET key value NX EX seconds 命令)

四、方案對(duì)比

方案適用場(chǎng)景注意事項(xiàng)
鍵空間通知精確延時(shí)任務(wù)(如30分鐘后關(guān)單)需配置 Redis,事件可能丟失
有序集合輪詢批量任務(wù)、高可靠性場(chǎng)景需自行處理任務(wù)分頁和重試
分布式鎖集群環(huán)境防重復(fù)執(zhí)行(如日?qǐng)?bào)生成)鎖超時(shí)時(shí)間需大于任務(wù)執(zhí)行時(shí)間

*補(bǔ)充:

  • 關(guān)鍵業(yè)務(wù)(如支付超時(shí))建議結(jié)合 數(shù)據(jù)庫(kù)日志+重試機(jī)制 補(bǔ)償;
  • 高頻任務(wù)優(yōu)先選 ZSET 輪詢,避免鍵空間通知的性能瓶頸;
  • 分布式鎖的鎖鍵需包含業(yè)務(wù)標(biāo)識(shí)(如 LOCK_KEY:業(yè)務(wù)名)。

到此這篇關(guān)于Springboot使用Redis實(shí)現(xiàn)定時(shí)任務(wù)的三種方式的文章就介紹到這了,更多相關(guān)Springboot Redis 定時(shí)任務(wù)內(nèi)容請(qǐng)搜索腳本之家以前的文章或繼續(xù)瀏覽下面的相關(guān)文章希望大家以后多多支持腳本之家! 

相關(guān)文章

  • springboot整合prometheus實(shí)現(xiàn)資源監(jiān)控的詳細(xì)步驟

    springboot整合prometheus實(shí)現(xiàn)資源監(jiān)控的詳細(xì)步驟

    Spring Boot與Prometheus的整合可以實(shí)現(xiàn)對(duì)Spring Boot應(yīng)用的實(shí)時(shí)監(jiān)控,有助于更好地維護(hù)應(yīng)用的性能,本文給大家介紹springboot整合prometheus實(shí)現(xiàn)資源監(jiān)控的詳細(xì)步驟,感興趣的朋友跟隨小編一起看看吧
    2024-11-11
  • 淺談java String.split丟失結(jié)尾空字符串的問題

    淺談java String.split丟失結(jié)尾空字符串的問題

    下面小編就為大家?guī)硪黄獪\談java String.split丟失結(jié)尾空字符串的問題。小編覺得挺不錯(cuò)的,現(xiàn)在就分享給大家,也給大家做個(gè)參考。一起跟隨小編過來看看吧
    2017-02-02
  • springMVC幾種頁面跳轉(zhuǎn)方式小結(jié)

    springMVC幾種頁面跳轉(zhuǎn)方式小結(jié)

    本篇文章主要介紹了springMVC 幾種頁面跳轉(zhuǎn)方式,小編覺得挺不錯(cuò)的,現(xiàn)在分享給大家,也給大家做個(gè)參考。一起跟隨小編過來看看吧
    2017-02-02
  • SpringBoot開發(fā)案例之配置Druid數(shù)據(jù)庫(kù)連接池的示例

    SpringBoot開發(fā)案例之配置Druid數(shù)據(jù)庫(kù)連接池的示例

    本篇文章主要介紹了SpringBoot開發(fā)案例之配置Druid數(shù)據(jù)庫(kù)連接池的示例,小編覺得挺不錯(cuò)的,現(xiàn)在分享給大家,也給大家做個(gè)參考。一起跟隨小編過來看看吧
    2018-03-03
  • SpringBoot處理跨域請(qǐng)求的四種方法

    SpringBoot處理跨域請(qǐng)求的四種方法

    在現(xiàn)代Web應(yīng)用中,由于安全性和隱私的考慮,瀏覽器限制了從一個(gè)域向另一個(gè)域發(fā)起的跨域HTTP請(qǐng)求,解決這個(gè)問題的一種常見方式是實(shí)現(xiàn)跨域資源共享(CORS),SpringBoot提供了多種方式來處理跨域請(qǐng)求,本文將介紹其中的幾種方法,感興趣的朋友可以參考下
    2023-12-12
  • 深入理解java中的synchronized關(guān)鍵字

    深入理解java中的synchronized關(guān)鍵字

    這篇文章主要介紹了java中的synchronized關(guān)鍵字,有需要的朋友可以參考一下
    2013-12-12
  • 什么是jsoup及jsoup的使用

    什么是jsoup及jsoup的使用

    jsoup是一款基于Java的HTML解析器,它提供了一套非常省力的API,不但能直接解析某個(gè)URL地址、HTML文本內(nèi)容,而且還能通過類似于DOM、CSS或者jQuery的方法來操作數(shù)據(jù),所以?jsoup?也可以被當(dāng)做爬蟲工具使用,這篇文章主要介紹了什么是jsoup及jsoup的使用,需要的朋友可以參考下
    2023-10-10
  • Java使用WebView實(shí)現(xiàn)桌面程序的技術(shù)指南

    Java使用WebView實(shí)現(xiàn)桌面程序的技術(shù)指南

    在現(xiàn)代軟件開發(fā)中,許多應(yīng)用需要在桌面程序中嵌入 Web 頁面,例如,你可能需要在 Java 桌面應(yīng)用中嵌入一部分 Web 前端,或者加載一個(gè) HTML5 界面以增強(qiáng)用戶體驗(yàn),所以本文給大家介紹了Java使用WebView實(shí)現(xiàn)桌面程序的技術(shù)指南,需要的朋友可以參考下
    2025-05-05
  • MyBatis-Plus實(shí)現(xiàn)優(yōu)雅處理JSON字段映射

    MyBatis-Plus實(shí)現(xiàn)優(yōu)雅處理JSON字段映射

    默認(rèn)情況下,MyBatis-Plus 是不支持直接映射 JSON 類型的,這時(shí)候就需要借助其他的方法,下面小編就來和大家講講MyBatis-Plus如何優(yōu)雅處理JSON字段映射吧
    2025-04-04
  • Jmeter對(duì)響應(yīng)數(shù)據(jù)實(shí)現(xiàn)斷言代碼實(shí)例

    Jmeter對(duì)響應(yīng)數(shù)據(jù)實(shí)現(xiàn)斷言代碼實(shí)例

    這篇文章主要介紹了Jmeter對(duì)響應(yīng)數(shù)據(jù)實(shí)現(xiàn)斷言代碼實(shí)例,文中通過示例代碼介紹的非常詳細(xì),對(duì)大家的學(xué)習(xí)或者工作具有一定的參考學(xué)習(xí)價(jià)值,需要的朋友可以參考下
    2020-09-09

最新評(píng)論