在redis2.6.12版本之前,使用setnx命令設定key-value、使用expire命令設定key的過期時間獲取分布式鎖,使用del命令釋放分布式鎖,但是這種實現有如下一些問題:
setnx命令設定完key-value後,還沒來得及使用expire命令設定過期時間,當前執行緒掛掉了,會導致當前執行緒設定的key一直有效,後續執行緒無法正常通過setnx獲取鎖,造成死鎖。
出現這個問題是因為兩個命令是分開執行並且不具備原子特性,如果能將這兩個命令合二為一就可以解決問題了。在redis2.6.12版本中實現了這個功能,redis為set命令增加了一系列選項。也就是說現在set命令就可以實現分布式鎖,下面我們來了解一下set命令(set(keyname, lockvalue, "nx", "ex", expireseconds)):
1. set命令是原子性操作,nx指令保證只要當key不存在時才會設定value
2. 設定的value要有唯一性,來確保鎖不會被誤刪(value=系統時間戳+uuid)
3. 當上述命令執行返回ok時,客戶端獲取鎖成功,否則失敗
4. 客戶端可以通過redis釋放指令碼來釋放鎖(del 命令)
5.如果鎖到達了最大生存時間將會自動釋放
只有當前key的value和傳入的value相同才會執行del命令。
優點:高效能,借助redis實現比較方便。
缺點:執行緒獲取鎖後,如果處理時間過長會導致鎖超時失效(失效時間我設定多長時間為好?如何設定的失效時間太短,方法沒等執行完,鎖就自動釋放了,那麼就會產生併發問題。如果設定的時間太長,其他獲取鎖的執行緒就可能要平白的多等一段時間。這個問題使用資料庫實現分布式鎖同樣存在),所以,通過超時時間來控制鎖的失效時間並不是十分的靠譜。
基於Redis實現分布式鎖
分布式鎖的基本功能 1.同一時刻只能存在乙個鎖 2.需要解決意外死鎖問題,也就是鎖能超時自動釋放 3.支援主動釋放鎖 分布式鎖解決什麼問題 多程序併發執行任務時,需要保證任務的有序性或者唯一性 準備 redis版本 2.6 redis是主從 sentinel模式 為了高可用 原理 redis2.6之...
基於Redis實現分布式鎖
之前專案中使用redis鎖實現秒殺等一些併發業務,在這裡整理一下基於redis實現分布式鎖的簡單入門例項,記錄一下,便於以後檢視 學習。springboot整合redisson分布式鎖 1 簡介 在分布式系統中存在併發場景,為了解決這一問題,基於redis鎖一定程度可以解決這一問題,但是也有缺點,如...
基於redis實現分布式鎖
實現方式 具備條件 確保鎖可用,必須要滿足一下幾個條件 1 互斥性,任意時刻只有乙個使用者能持有鎖 2 不會產生死鎖,假設某個使用者在持有鎖的期間由於服務崩潰或者其他原因沒有主動釋放鎖,也能保證後續其他使用者可以加鎖 3 加鎖和解鎖必須是同一使用者,b使用者無法解除a使用者加的鎖 實現 1 引入je...