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

redis和redisson實(shí)現(xiàn)分布式鎖的操作方法

 更新時(shí)間:2024年03月27日 10:48:51   作者:開心就好啦啦啦  
使用 Redis 實(shí)現(xiàn)分布式鎖,最直接的想法是利用 setnx 和 expire 命令實(shí)現(xiàn)加鎖,這篇文章主要介紹了redis和redisson實(shí)現(xiàn)分布式鎖的操作方法,需要的朋友可以參考下

基于setnx命令的分布式鎖

1. 加鎖

使用 Redis 實(shí)現(xiàn)分布式鎖,最直接的想法是利用 setnx 和 expire 命令實(shí)現(xiàn)加鎖。

在 Redis 中,setnx 是「set if not exists」如果不存在,則 setnx 的意思,當(dāng)一個線程執(zhí)行 setnx 返回 1,說明 key 不存在,該線程獲得鎖;當(dāng)一個線程執(zhí)行 setnx 返回 0,說明 key 已經(jīng)存在,那么獲取鎖失敗。

SETNX lockKey uniqueValue
(integer) 1
SETNX lockKey uniqueValue
(integer) 0

2. 釋放鎖

釋放鎖的話,直接通過 DEL 命令刪除對應(yīng)的 key 即可。

DEL lockKey
(integer) 1

為了防止誤刪到其他的鎖,這里我們建議使用 Lua 腳本通過 key 對應(yīng)的 value(唯一值)來判斷。選用 Lua 腳本是為了保證解鎖操作的原子性。因?yàn)?Redis 在執(zhí)行 Lua 腳本時(shí),可以以原子性的方式執(zhí)行,從而保證了鎖釋放操作的原子性。

if redis.call("get",KEYS[1]) == ARGV[1] then
    return redis.call("del",KEYS[1])
else
    return 0

釋放鎖時(shí),先比較鎖對應(yīng)的 value 值是否相等,value值可以在加鎖的時(shí)候把當(dāng)前的線程 ID 當(dāng)做value,并在刪除之前驗(yàn)證 key 對應(yīng)的 value 是不是自己線程的 ID,避免鎖的誤釋放

3. setnx缺點(diǎn)

setnx 的 key 必須設(shè)置一個超時(shí)時(shí)間,以保證即使沒有被顯式釋放,這把鎖也要在一定時(shí)間后自動釋放??梢允褂胑xpire命令設(shè)置鎖超時(shí)時(shí)間

4. 存在問題:

setnx 和 expire 不是原子性的操作,假設(shè)某個線程執(zhí)行setnx 命令,成功獲得了鎖,但是還沒來得及執(zhí)行expire 命令,服務(wù)器就掛掉了,這樣一來,這把鎖就沒有設(shè)置過期時(shí)間了,變成了死鎖,別的線程再也沒有辦

法獲得鎖了。
解決方案:redis的set命令支持在獲取鎖的同時(shí)設(shè)置key的過期時(shí)間

基于set命令的分布式鎖

Redis 從 2.6.12 起,SET 涵蓋了 SETEX 的功能,并且 SET 本身已經(jīng)包含了設(shè)置過期時(shí)間的功能

使用set命令加鎖并設(shè)置鎖過期時(shí)間:

127.0.0.1:6379> SET lockKey uniqueValue EX 3 NX
OK

lockKey:加鎖的鎖名;
uniqueValue:能夠唯一標(biāo)示鎖的隨機(jī)字符串;
NX:只有當(dāng) lockKey 對應(yīng)的 key 值不存在的時(shí)候才能 SET 成功;
EX:過期時(shí)間設(shè)置(秒為單位)EX 3 標(biāo)示這個鎖有一個 3 秒的自動過期時(shí)間。與 EX 對應(yīng)的是 PX(毫秒為單位),這兩個都是過期時(shí)間設(shè)置。
一定要保證設(shè)置指定 key 的值和過期時(shí)間是一個原子操作?。?! 不然的話,依然可能會出現(xiàn)鎖無法被釋放的問題。

不過,這種解決辦法同樣存在漏洞:如果操作共享資源的時(shí)間大于過期時(shí)間,就會出現(xiàn)鎖提前過期的問題,進(jìn)而導(dǎo)致分布式鎖直接失效。如果鎖的超時(shí)時(shí)間設(shè)置過長,又會影響到性能。

為了解決這個問題,我們可以讓獲得鎖的線程開啟一個守護(hù)線程,用來給快要過期的鎖“續(xù)期”。在JAVA的Redisson包中有一個”看門狗”機(jī)制,已經(jīng)幫我們實(shí)現(xiàn)了這個功能。

redission看門狗分布式鎖

Redisson 中的分布式鎖自帶自動續(xù)期機(jī)制,使用起來非常簡單,原理也比較簡單,其提供了一個專門用來監(jiān)控和續(xù)期鎖的 Watch Dog( 看門狗),如果操作共享資源的線程還未執(zhí)行完成的話,Watch Dog 會不斷地延長鎖的過期時(shí)間,進(jìn)而保證鎖不會因?yàn)槌瑫r(shí)而被釋放。

1.加鎖機(jī)制

  • 線程去獲取鎖,獲取成功:執(zhí)行l(wèi)ua腳本,保存數(shù)據(jù)到redis數(shù)據(jù)庫。
  • 此時(shí)另外一個線程去獲取鎖,可以一直通過while循環(huán)嘗試獲取鎖(鎖重試)
    如果在獲取鎖的最大等待時(shí)間內(nèi)加鎖成功,執(zhí)行l(wèi)ua腳本,保存數(shù)據(jù)到redis數(shù)據(jù)庫。如果失敗,則返回加鎖失敗。

2.watch dog自動延期機(jī)制:

Redisson在獲取鎖之后,會維護(hù)一個看門狗線程,在每一個鎖設(shè)置的過期時(shí)間的1/3處,如果線程還沒執(zhí)行完任務(wù),則不斷延長鎖的有效期。剛開始鎖的過期時(shí)間默認(rèn)是30秒,可以通過 lockWactchdogTimeout 參數(shù)來改變。

每過 10 秒,看門狗就會執(zhí)行續(xù)期操作,將鎖的超時(shí)時(shí)間重置為 30 秒。看門狗續(xù)期前也會先判斷是否需要執(zhí)行續(xù)期操作,需要才會執(zhí)行續(xù)期,否則取消續(xù)期操作。

看門狗啟動后,對整體性能也會有一定影響,默認(rèn)情況下看門狗線程是不啟動的。如果使用redisson進(jìn)行加鎖的同時(shí)設(shè)置了鎖的過期時(shí)間,也會導(dǎo)致看門狗機(jī)制失效。

加鎖的時(shí)間默認(rèn)是30秒,如果加鎖的業(yè)務(wù)沒有執(zhí)行完,那么每隔 30 ÷ 3 = 10秒,就會進(jìn)行一次續(xù)期,把鎖重置成30秒,保證解鎖前鎖不會自動失效。

3.redisson分布式鎖的關(guān)鍵點(diǎn):

  • 對key不設(shè)置過期時(shí)間,由Redisson在加鎖成功后給維護(hù)一個watchdog看門狗,watchdog負(fù)責(zé)定時(shí)監(jiān)聽并處理,在鎖沒有被釋放且快要過期的時(shí)候自動對鎖進(jìn)行續(xù)期,保證解鎖前鎖不會自動失效
  • 通過Lua腳本實(shí)現(xiàn)了加鎖和解鎖的原子操作,底層是使用setnx和lua腳本
  • 通過記錄獲取鎖的客戶端id,每次加鎖時(shí)判斷是否是當(dāng)前客戶端已經(jīng)獲得鎖,實(shí)現(xiàn)了可重入鎖。

Redisson 的分布式可重入鎖 RLock 為例來說明如何使用 Redisson 實(shí)現(xiàn)分布式鎖:

public String testLock() throws InterruptedException {
    RLock lock = redissonClient.getLock("it_lock");
    //嘗試獲取鎖,tryLock參數(shù)分別是:獲取鎖的最大等待時(shí)間(期間重試) ,鎖自動釋放時(shí)間,時(shí)間單位
    //lock.tryLock(10, 30,TimeUnit.SECONDS); //設(shè)置鎖釋放時(shí)間 不會續(xù)期操作
    boolean isLock = lock.tryLock(10, TimeUnit.SECONDS); //沒有設(shè)置鎖釋放時(shí)間 守護(hù)線程會自動續(xù)期
    //是否成功
    if(isLock){
        try {
            //業(yè)務(wù)邏輯
        }finally {
            lock.unlock();
        }
    }
    return "finish";
}

指定鎖超時(shí)時(shí)間,不會使用自動續(xù)期機(jī)制

lock.tryLock(10, 30,TimeUnit.SECONDS); //設(shè)置鎖釋放時(shí)間 不會續(xù)期操作

只有未指定鎖超時(shí)時(shí)間,才會使用到 Watch Dog 自動續(xù)期機(jī)制。

   // 手動給鎖設(shè)置過期時(shí)間,不具備 Watch Dog 自動續(xù)期機(jī)制
   lock.tryLock(10, TimeUnit.SECONDS);

如果使用 Redis 來實(shí)現(xiàn)分布式鎖的話,還是比較推薦直接基于 Redisson 來做的

到此這篇關(guān)于redis和redisson實(shí)現(xiàn)分布式鎖的文章就介紹到這了,更多相關(guān)redis和redisson實(shí)現(xiàn)分布式鎖內(nèi)容請搜索腳本之家以前的文章或繼續(xù)瀏覽下面的相關(guān)文章希望大家以后多多支持腳本之家!

相關(guān)文章

  • Redis優(yōu)惠券秒殺企業(yè)實(shí)戰(zhàn)

    Redis優(yōu)惠券秒殺企業(yè)實(shí)戰(zhàn)

    本文主要介紹了Redis優(yōu)惠券秒殺企業(yè)實(shí)戰(zhàn),文中通過示例代碼介紹的非常詳細(xì),對大家的學(xué)習(xí)或者工作具有一定的參考學(xué)習(xí)價(jià)值,需要的朋友們下面隨著小編來一起學(xué)習(xí)學(xué)習(xí)吧
    2022-07-07
  • 詳解用Redis實(shí)現(xiàn)Session功能

    詳解用Redis實(shí)現(xiàn)Session功能

    本篇文章主要介紹了用Redis實(shí)現(xiàn)Session功能,具有一定的參考價(jià)值,小編覺得挺不錯的,現(xiàn)在分享給大家,也給大家做個參考。
    2016-12-12
  • redis中token失效引發(fā)的一次生產(chǎn)事故

    redis中token失效引發(fā)的一次生產(chǎn)事故

    項(xiàng)目再測試的時(shí)候發(fā)現(xiàn)不定時(shí)token失效,本文主要介紹了redis中token失效引發(fā)的一次生產(chǎn)事故,文中通過示例代碼介紹的非常詳細(xì),需要的朋友們下面隨著小編來一起學(xué)習(xí)學(xué)習(xí)吧
    2024-03-03
  • Redis數(shù)據(jù)庫安裝部署及基本操作詳解

    Redis數(shù)據(jù)庫安裝部署及基本操作詳解

    這篇文章主要介紹了Redis數(shù)據(jù)庫安裝部署及基本操作,本文給大家介紹的非常詳細(xì),對大家的學(xué)習(xí)或工作具有一定的參考借鑒價(jià)值,需要的朋友可以參考下
    2021-08-08
  • 控制Redis的hash的field中的過期時(shí)間

    控制Redis的hash的field中的過期時(shí)間

    這篇文章主要介紹了控制Redis的hash的field中的過期時(shí)間問題,具有很好的參考價(jià)值,希望對大家有所幫助。如有錯誤或未考慮完全的地方,望不吝賜教
    2023-01-01
  • redis中List列表常見命令及使用場景

    redis中List列表常見命令及使用場景

    這篇文章主要給大家介紹了關(guān)于redis中List列表常見命令及使用場景的相關(guān)資料,Redis列表是簡單的字符串列表,按照插入順序排序,文中通過代碼介紹的非常詳細(xì),需要的朋友可以參考下
    2024-01-01
  • Redis內(nèi)存碎片原理深入分析

    Redis內(nèi)存碎片原理深入分析

    這篇文章主要為大家介紹了Redis內(nèi)存碎片原理深入分析,有需要的朋友可以借鑒參考下,希望能夠有所幫助,祝大家多多進(jìn)步,早日升職加薪
    2023-02-02
  • 詳解redis集群選舉機(jī)制

    詳解redis集群選舉機(jī)制

    這篇文章主要介紹了詳解redis集群選舉機(jī)制,文中通過示例代碼介紹的非常詳細(xì),對大家的學(xué)習(xí)或者工作具有一定的參考學(xué)習(xí)價(jià)值,需要的朋友們下面隨著小編來一起學(xué)習(xí)學(xué)習(xí)吧
    2021-03-03
  • Linux下redis的安裝與使用圖文教程

    Linux下redis的安裝與使用圖文教程

    這篇文章主要介紹了Linux下redis的安裝與使用,結(jié)合圖文形式分析了Linux環(huán)境下redis的下載、編譯、安裝、部署、訪問等相關(guān)操作技巧,需要的朋友可以參考下
    2019-08-08
  • redis復(fù)制有可能碰到的問題匯總

    redis復(fù)制有可能碰到的問題匯總

    這篇文章主要介紹了redis復(fù)制有可能碰到的問題匯總,本文給大家介紹的非常詳細(xì),對大家的學(xué)習(xí)或工作具有一定的參考借鑒價(jià)值,需要的朋友可以參考下
    2022-04-04

最新評論