国产av日韩一区二区三区精品,成人性爱视频在线观看,国产,欧美,日韩,一区,www.成色av久久成人,2222eeee成人天堂

目錄
一、Redisson 是什么?" >一、Redisson 是什么?
2.1 引入 Maven 依賴" >2.1 引入 Maven 依賴
2.2 自定義配置類" >2.2 自定義配置類
2.3 測試配置類" >2.3 測試配置類
三、分布式可重入鎖" >三、分布式可重入鎖
3.1 可重入鎖測試" >3.1 可重入鎖測試
3.1.1 驗證一:可重入鎖是阻塞的嗎?
3.1.2 驗證二:服務停了,鎖會釋放嗎?
3.2 看門狗原理" >3.2 看門狗原理
3.3 設置鎖過期時間" >3.3 設置鎖過期時間
四、王者方案" >四、王者方案
五、分布式讀寫鎖" >五、分布式讀寫鎖
六、分布式信號量" >六、分布式信號量
首頁 Java java教程 分布式鎖中的王者方案 - Redisson

分布式鎖中的王者方案 - Redisson

Aug 24, 2023 pm 03:31 PM
分布式鎖 redisson


分布式鎖中的王者方案 - Redisson

網上有各種各樣關于Redis實現分布式鎖的方案,但何為王者方案?

答案就:?Redisson。

我們先來看下 Redis 官網對分布式鎖的說法:

分布式鎖中的王者方案 - Redisson

而 Java 版的 分布式鎖的框架就是 Redisson。

本篇實戰(zhàn)內容將會基于我的開源項目 PassJava 來整合 Redisson。

我把后端、前端、小程序都上傳到同一個倉庫里面了,大家可以通過 Github碼云訪問。地址如下:

Github: https://github.com/Jackson0714/PassJava-Platform

碼云:https://gitee.com/jayh2018/PassJava-Platform

配套教程:www.passjava.cn

在實戰(zhàn)之前,我們先來看下使用 Redisson 的原理。

一、Redisson 是什么?

如果你之前是在用 Redis 的話,那使用 Redisson 的話將會事半功倍,Redisson 提供了使用 Redis的最簡單和最便捷的方法。

Redisson的宗旨是促進使用者對 Redis 的關注分離(Separation of Concern),從而讓使用者能夠將精力更集中地放在處理業(yè)務邏輯上。

Redisson 是一個在 Redis 的基礎上實現的 Java 駐內存數據網格(In-Memory Data Grid)。

分布式鎖中的王者方案 - Redisson
  • Netty 框架:Redisson采用了基于NIO的Netty框架,不僅能作為Redis底層驅動客戶端,具備提供對Redis各種組態(tài)形式的連接功能,對Redis命令能以同步發(fā)送、異步形式發(fā)送、異步流形式發(fā)送或管道形式發(fā)送的功能,LUA腳本執(zhí)行處理,以及處理返回結果的功能

  • 基礎數據結構:將原生的Redis HashList,SetString,GeoHyperLogLog等數據結構封裝為Java里大家最熟悉的映射(Map),列表(List)集(Set),通用對象桶(Object Bucket),地理空間對象桶(Geospatial Bucket)基數估計算法(HyperLogLog)等結構,

  • 分布式數據結構:這基礎上還提供了分布式的多值映射(Multimap),本地緩存映射(LocalCachedMap),有序集(SortedSet),計分排序集(ScoredSortedSet),字典排序集(LexSortedSet),列隊(Queue),阻塞隊列(Blocking Queue),有界阻塞列隊(Bounded Blocking Queue),雙端隊列(Deque),阻塞雙端列隊(Blocking Deque),阻塞公平列隊(Blocking Fair Queue),延遲列隊(Delayed Queue),布隆過濾器(Bloom Filter),原子整長形(AtomicLong),原子雙精度浮點數(AtomicDouble),BitSet等Redis原本沒有的分布式數據結構。

  • 分布式鎖:Redisson還實現了Redis文檔中提到像分布式鎖Lock這樣的更高階應用場景。事實上Redisson并沒有不止步于此,在分布式鎖的基礎上還提供了聯鎖(MultiLock),讀寫鎖(ReadWriteLock)公平鎖(Fair Lock)紅鎖(RedLock),信號量(Semaphore),可過期性信號量(PermitExpirableSemaphore)閉鎖(CountDownLatch)這些實際當中對多線程高并發(fā)應用至關重要的基本部件。正是通過實現基于Redis的高階應用方案,使Redisson成為構建分布式系統的重要工具。Lock這樣的更高階應用場景。事實上Redisson并沒有不止步于此,在分布式鎖的基礎上還提供了聯鎖(MultiLock),讀寫鎖(ReadWriteLock)公平鎖(Fair Lock),紅鎖(RedLock)信號量(Semaphore),可過期性信號量(PermitExpirableSemaphore)閉鎖(CountDownLatch)這些實際當中對多線程高并發(fā)應用至關重要的基本部件。正是通過實現基于Redis的高階應用方案,使Redisson成為構建分布式系統的重要工具。

  • 節(jié)點:Redisson作為獨立節(jié)點可以用于獨立執(zhí)行其他節(jié)點發(fā)布到分布式執(zhí)行服務分布式調度服務

節(jié)點:Redisson作為獨立節(jié)點可以用于獨立執(zhí)行其他節(jié)點發(fā)布到分布式執(zhí)行服務分布式調度服務里的遠程任務。

  • 二、整合 Redisson
  • Spring Boot 整合 Redisson 有兩種方案:
程序化配置。

????文件方式配置。????????本篇介紹如何用程序化的方式整合 Redisson。??

2.1 引入 Maven 依賴

在 passjava-question 微服務的 pom.xml 引入 redisson的 maven 依賴。

<!-- https://mvnrepository.com/artifact/org.redisson/redisson -->
<dependency>
    <groupId>org.redisson</groupId>
    <artifactId>redisson</artifactId>
    <version>3.15.5</version>
</dependency>

2.2 自定義配置類

下面的代碼是單節(jié)點 Redis 的配置。

@Configuration
public class MyRedissonConfig {
    /**
     * 對 Redisson 的使用都是通過 RedissonClient 對象
     * @return
     * @throws IOException
     */
    @Bean(destroyMethod="shutdown") // 服務停止后調用 shutdown 方法。
    public RedissonClient redisson() throws IOException {
        // 1.創(chuàng)建配置
        Config config = new Config();
        // 集群模式
        // config.useClusterServers().addNodeAddress("127.0.0.1:7004", "127.0.0.1:7001");
        // 2.根據 Config 創(chuàng)建出 RedissonClient 示例。
        config.useSingleServer().setAddress("redis://127.0.0.1:6379");
        return Redisson.create(config);
    }
}

2.3 測試配置類

新建一個單元測試方法。

@Autowired
RedissonClient redissonClient;

@Test
public void TestRedisson() {
    System.out.println(redissonClient);
}

我們運行這個測試方法,打印出 redissonClient

org.redisson.Redisson@77f66138

三、分布式可重入鎖

3.1 可重入鎖測試

基于Redis的Redisson分布式可重入鎖RLockJava 對象實現了java.util.concurrent.locks.Lock接口。同時還提供了異步(Async)、反射式(Reactive)和RxJava2標準的接口。RLockJava 對象實現了java.util.concurrent.locks.Lock接口。同時還提供了異步(Async)、反射式(Reactive)和RxJava2標準的接口。

RLock lock = redisson.getLock("anyLock");
// 最常見的使用方法
lock.lock();

我們用 passjava 這個開源項目測試下可重入鎖的兩個點:

  • (1)多個線程搶占鎖,后面鎖需要等待嗎?
  • (2)如果搶占到鎖的線程所在的服務停了,鎖會不會被釋放?

3.1.1 驗證一:可重入鎖是阻塞的嗎?

為了驗證以上兩點,我寫了個 demo 程序:代碼的流程就是設置WuKong-lock

@ResponseBody
@GetMapping("test-lock")
public String TestLock() {
    // 1.獲取鎖,只要鎖的名字一樣,獲取到的鎖就是同一把鎖。
    RLock lock = redisson.getLock("WuKong-lock");

    // 2.加鎖
    lock.lock();
    try {
        System.out.println("加鎖成功,執(zhí)行后續(xù)代碼。線程 ID:" + Thread.currentThread().getId());
        Thread.sleep(10000);
    } catch (Exception e) {
        //TODO
    } finally {
        lock.unlock();
        // 3.解鎖
        System.out.println("Finally,釋放鎖成功。線程 ID:" + Thread.currentThread().getId());
    }

    return "test lock ok";
}

我們用 passjava 這個開源項目測試下可重入鎖的兩個點:

  • (1)多個線程搶占鎖,后面鎖需要等待嗎?
  • (2)如果搶占到鎖的線程所在的服務停了,鎖會不會被釋放?

3.1.1 驗證一:可重入鎖是阻塞的嗎?

為了驗證以上兩點,我寫了個 demo 程序:代碼的流程就是設置WuKong-lock鎖,然后加鎖,打印線程 ID,等待 10 秒后釋放鎖,最后返回響應:“test lock ok”。

http://localhost:11000/question/v1/redisson/test/test-lock

先驗證第一個點,用兩個 http 請求來測試搶占鎖。????請求的 URL:??
http://localhost:11000/question/v1/redisson/test/test-lock
分布式鎖中的王者方案 - Redisson

第一個線程對應的線程 ID 為 86,10秒后,釋放鎖。在這期間,第二個線程需要等待鎖釋放。

第一個線程釋放鎖之后,第二個線程獲取到了鎖,10 秒后,釋放鎖。

畫了一個流程圖,幫助大家理解。如下圖所示:

分布式鎖中的王者方案 - Redisson
  • 第一步:線程 A 在 0 秒時,搶占到鎖,0.1 秒后,開始執(zhí)行等待 10 s。
  • 第二步:線程 B 在 0.1 秒嘗試搶占鎖,未能搶到鎖(被 A 搶占了)。
  • 第三步:線程 A 在 10.1 秒后,釋放鎖。
  • 第四步:線程 B 在 10.1 秒后搶占到鎖,然后等待 10 秒后釋放鎖。

由此可以得出結論,Redisson 的可重入鎖(lock)是阻塞其他線程的,需要等待其他線程釋放的。

3.1.2 驗證二:服務停了,鎖會釋放嗎?

如果線程 A 在等待的過程中,服務突然停了,那么鎖會釋放嗎?如果不釋放的話,就會成為死鎖,阻塞了其他線程獲取鎖。

我們先來看下線程 A 的獲取鎖后的,Redis 客戶端查詢到的結果,如下圖所示:

分布式鎖中的王者方案 - Redisson

WuKong-lock 有值,而且大家可以看到 TTL 在不斷變小,說明 WuKong-lock 是自帶過期時間的。

通過觀察,經過 30 秒后,WuKong-lock 過期消失了。說明 Redisson 在停機后,占用的鎖會自動釋放。

分布式鎖中的王者方案 - Redisson

那這又是什么原理呢?這里就要提一個概念了,看門狗

分布式鎖中的王者方案 - Redisson

3.2 看門狗原理

如果負責儲存這個分布式鎖的 Redisson 節(jié)點宕機以后,而且這個鎖正好處于鎖住的狀態(tài)時,這個鎖會出現鎖死的狀態(tài)。為了避免這種情況的發(fā)生,Redisson內部提供了一個監(jiān)控鎖的看門狗,它的作用是在Redisson實例被關閉前,不斷的延長鎖的有效期。

默認情況下,看門狗的檢查鎖的超時時間是30秒鐘,也可以通過修改Config.lockWatchdogTimeout來另行指定。

如果我們未制定 lock 的超時時間,就使用 30 秒作為看門狗的默認時間。只要占鎖成功,就會啟動一個定時任務:每隔 10 秒重新給鎖設置過期的時間,過期時間為 30 秒。

如下圖所示:

分布式鎖中的王者方案 - Redisson
看門狗原理圖-1

當服務器宕機后,因為鎖的有效期是 30 秒,所以會在 30 秒內自動解鎖。(30秒等于宕機之前的鎖占用時間+后續(xù)鎖占用的時間)。

如下圖所示:

分布式鎖中的王者方案 - Redisson
看門狗原理圖-2

3.3 設置鎖過期時間

我們也可以通過給鎖設置過期時間,讓其自動解鎖。

如下所示,設置鎖 8 秒后自動過期。

lock.lock(8, TimeUnit.SECONDS);

如果業(yè)務執(zhí)行時間超過 8 秒,手動釋放鎖將會報錯,如下圖所示:

分布式鎖中的王者方案 - Redisson

所以我們如果設置了鎖的自動過期時間,則執(zhí)行業(yè)務的時間一定要小于鎖的自動過期時間,否則就會報錯。

四、王者方案

上一篇我講解了分布式鎖的五種方案:Redis 分布式鎖|從青銅到鉆石的五種演進方案,這一篇主要是講解如何用 Redisson 在 Spring Boot 項目中實現分布式鎖的方案。

因為 Redisson 非常強大,實現分布式鎖的方案非常簡潔,所以稱作王者方案。

原理圖如下:

分布式鎖中的王者方案 - Redisson

代碼如下所示:

// 1.設置分布式鎖
RLock lock = redisson.getLock("lock");
// 2.占用鎖
lock.lock();
// 3.執(zhí)行業(yè)務
...
// 4.釋放鎖
lock.unlock();

和之前 Redis 的方案相比,簡潔很多。

下面講解下 Redisson 的其他幾種分布式鎖,相信大家在以后的項目中也會用到。

五、分布式讀寫鎖

基于 Redis 的 Redisson 分布式可重入讀寫鎖RReadWriteLock Java對象實現了java.util.concurrent.locks.ReadWriteLock接口。其中讀鎖和寫鎖都繼承了 RLock接口。

寫鎖是一個排他鎖(互斥鎖),讀鎖是一個共享鎖。

  • 讀鎖 + 讀鎖:相當于沒加鎖,可以并發(fā)讀。
  • 讀鎖 + 寫鎖:寫鎖需要等待讀鎖釋放鎖。
  • 寫鎖 + 寫鎖:互斥,需要等待對方的鎖釋放。
  • 寫鎖 + 讀鎖:讀鎖需要等待寫鎖釋放。
分布式鎖中的王者方案 - Redisson

示例代碼如下:

RReadWriteLock rwlock = redisson.getReadWriteLock("anyRWLock");
// 最常見的使用方法
rwlock.readLock().lock();
// 或
rwlock.writeLock().lock();

另外Redisson還通過加鎖的方法提供了leaseTime的參數來指定加鎖的時間。超過這個時間后鎖便自動解開了。

// 10秒鐘以后自動解鎖
// 無需調用unlock方法手動解鎖
rwlock.readLock().lock(10, TimeUnit.SECONDS);
// 或
rwlock.writeLock().lock(10, TimeUnit.SECONDS);

// 嘗試加鎖,最多等待100秒,上鎖以后10秒自動解鎖
boolean res = rwlock.readLock().tryLock(100, 10, TimeUnit.SECONDS);
// 或
boolean res = rwlock.writeLock().tryLock(100, 10, TimeUnit.SECONDS);
...
lock.unlock();

六、分布式信號量

基于Redis的Redisson的分布式信號量(Semaphore)Java對象RSemaphore采用了與java.util.concurrent.Semaphore相似的接口和用法。同時還提供了異步(Async)、反射式(Reactive)和RxJava2標準的接口。

關于信號量的使用大家可以想象一下這個場景,有三個停車位,當三個停車位滿了后,其他車就不停了??梢园衍囄槐茸餍盘?,現在有三個信號,停一次車,用掉一個信號,車離開就是釋放一個信號。

分布式鎖中的王者方案 - Redisson

我們用 Redisson 來演示上述停車位的場景。

先定義一個占用停車位的方法:

/**
* 停車,占用停車位
* 總共 3 個車位
*/
@ResponseBody
@RequestMapping("park")
public String park() throws InterruptedException {
  // 獲取信號量(停車場)
  RSemaphore park = redisson.getSemaphore("park");
  // 獲取一個信號(停車位)
  park.acquire();

  return "OK";
}

再定義一個離開車位的方法:

/**
 * 釋放車位
 * 總共 3 個車位
 */
@ResponseBody
@RequestMapping("leave")
public String leave() throws InterruptedException {
    // 獲取信號量(停車場)
    RSemaphore park = redisson.getSemaphore("park");
    // 釋放一個信號(停車位)
    park.release();

    return "OK";
}

為了簡便,我用 Redis 客戶端添加了一個 key:“park”,值等于 3,代表信號量為 park,總共有三個值。

分布式鎖中的王者方案 - Redisson

然后用 postman 發(fā)送 park 請求占用一個停車位。

分布式鎖中的王者方案 - Redisson

然后在 redis 客戶端查看 park 的值,發(fā)現已經改為 2 了。繼續(xù)調用兩次,發(fā)現 park 的等于 0,當調用第四次的時候,會發(fā)現請求一直處于等待中,說明車位不夠了。如果想要不阻塞,可以用 tryAcquire 或 tryAcquireAsync。

我們再調用離開車位的方法,park 的值變?yōu)榱?1,代表車位剩余 1 個。

注意:多次執(zhí)行釋放信號量操作,剩余信號量會一直增加,而不是到 3 后就封頂了。

其他分布式鎖:

  • 公平鎖(Fair Lock)

  • 聯鎖(MultiLock)

  • 紅鎖(RedLock)

  • 讀寫鎖(ReadWriteLock)

  • 可過期性信號量(PermitExpirableSemaphore)

  • 閉鎖(CountDownLatch)

分布式鎖中的王者方案 - Redisson

還有其他分布式鎖就不在本篇展開了,感興趣的同學可以查看官方文檔。

以上是分布式鎖中的王者方案 - Redisson的詳細內容。更多信息請關注PHP中文網其他相關文章!

本站聲明
本文內容由網友自發(fā)貢獻,版權歸原作者所有,本站不承擔相應法律責任。如您發(fā)現有涉嫌抄襲侵權的內容,請聯系admin@php.cn

熱AI工具

Undress AI Tool

Undress AI Tool

免費脫衣服圖片

Undresser.AI Undress

Undresser.AI Undress

人工智能驅動的應用程序,用于創(chuàng)建逼真的裸體照片

AI Clothes Remover

AI Clothes Remover

用于從照片中去除衣服的在線人工智能工具。

Clothoff.io

Clothoff.io

AI脫衣機

Video Face Swap

Video Face Swap

使用我們完全免費的人工智能換臉工具輕松在任何視頻中換臉!

熱工具

記事本++7.3.1

記事本++7.3.1

好用且免費的代碼編輯器

SublimeText3漢化版

SublimeText3漢化版

中文版,非常好用

禪工作室 13.0.1

禪工作室 13.0.1

功能強大的PHP集成開發(fā)環(huán)境

Dreamweaver CS6

Dreamweaver CS6

視覺化網頁開發(fā)工具

SublimeText3 Mac版

SublimeText3 Mac版

神級代碼編輯軟件(SublimeText3)

分布式鎖:5個案例,從入門到入土 分布式鎖:5個案例,從入門到入土 Aug 24, 2023 pm 02:48 PM

今天給大家分享的是分布式鎖,本文使用五個案例、圖、源碼分析等來分析。常見的synchronized、Lock等這些鎖都是基于單個JVM的實現的,如果分布式場景下怎么辦呢?這時候分布式鎖就出現了。

SpringBoot怎么集成Redisson實現延遲隊列 SpringBoot怎么集成Redisson實現延遲隊列 May 30, 2023 pm 02:40 PM

使用場景1、下單成功,30分鐘未支付。支付超時,自動取消訂單2、訂單簽收,簽收后7天未進行評價。訂單超時未評價,系統默認好評3、下單成功,商家5分鐘未接單,訂單取消4、配送超時,推送短信提醒……對于延時比較長的場景、實時性不高的場景,我們可以采用任務調度的方式定時輪詢處理。如:xxl-job今天我們采

Redis實現分布式鎖的Etcd對比 Redis實現分布式鎖的Etcd對比 Jun 20, 2023 pm 05:51 PM

隨著分布式系統的逐漸普及,分布式鎖已成為保證系統穩(wěn)定性和數據一致性的重要手段。Redis作為一款高性能的分布式內存數據庫,自然成為了分布式鎖的重要實現之一。但是,最近幾年,Etcd作為新興的分布式一致性解決方案,受到了越來越多的關注。本文將從實現原理、對比分析等方面探討Redis實現分布式鎖與Etcd的異同。Redis實現分布式鎖的原理Redis分布式鎖的實

分布式鎖中的王者方案 - Redisson 分布式鎖中的王者方案 - Redisson Aug 24, 2023 pm 03:31 PM

如果你之前是在用 Redis 的話,那使用 Redisson 的話將會事半功倍,Redisson 提供了使用 Redis的最簡單和最便捷的方法。Redisson的宗旨是促進使用者對 Redis 的關注分離(Separation of Concern),從而讓使用者能夠將精力更集中地放在處理業(yè)務邏輯上。

Java API 開發(fā)中使用 ZooKeeper 進行分布式鎖處理 Java API 開發(fā)中使用 ZooKeeper 進行分布式鎖處理 Jun 17, 2023 pm 10:36 PM

隨著現代應用程序的不斷發(fā)展和對高可用性和并發(fā)性的需求日益增長,分布式系統架構變得越來越普遍。在分布式系統中,多個進程或節(jié)點同時運行并共同完成任務,進程之間的同步變得尤為重要。由于分布式環(huán)境下許多節(jié)點可以同時訪問共享資源,因此,在分布式系統中,如何處理并發(fā)和同步問題成為了一項重要的任務。在此方面,ZooKeeper已經成為了一個非常流行的解決方案。ZooKee

Java?Redis?Redisson配置實例分析 Java?Redis?Redisson配置實例分析 Apr 25, 2023 am 08:19 AM

需要的Mavenorg.springframework.bootspring-boot-starter-data-redisio.lettucelettuce-coreredis.clientsjedisorg.springframework.sessionspring-session-data-redisorg.redissonredisson3.17.5application-redis.ymlspring:redis:host:106.12.174.220port:6379password

了解 Redisson 緩存技術 了解 Redisson 緩存技術 Jun 21, 2023 am 09:54 AM

Redisson是一種基于Redis的Java應用程序緩存解決方案。它提供了許多有用功能,使得在Java應用中使用Redis作為緩存變得更加方便和高效。Redisson提供的緩存功能包括:1.分布式映射(Map):Redisson提供了一些用于創(chuàng)建分布式映射的API。這些映射可以包含鍵值對、哈希表項或對象,它們可以支持在多個節(jié)點之間共

Redis實現分布式鎖詳解 Redis實現分布式鎖詳解 Jun 21, 2023 am 11:02 AM

隨著移動互聯網的快速發(fā)展和數據量的爆炸式增長,分布式系統變得越來越普及。分布式系統中,并發(fā)操作的問題就變得越來越凸顯,當多個線程同時請求共享資源時,就需要對這些資源進行加鎖,保證數據的一致性。分布式鎖是一種實現分布式系統并發(fā)操作的有效方案之一,本文將詳細介紹如何使用Redis實現分布式鎖。Redis基礎Redis是一個基于內存的鍵值對存儲系統,在分布

See all articles