前言
關於分布式鎖,在網際網路行業的使用場景還是比較多的,比如電商的庫存扣減,秒殺活動,集群定時任務執行等需要程序互斥的場景。而實現分布式鎖的手段也很多,大家比較常見的就是redis跟zookeeper,今天我們主要介紹的是基於zookeeper實現的分布式鎖。
這篇文章主要借用curator框架對zk分布式鎖的實現思路,大家理解了以後完全可以自己手動實現一遍,但是在工作中還是建議使用成熟的開源框架,很多坑別人已經幫我們踩好了,除非萬不得已,需要高度定製符合自己專案的需求的時候,才開始自行封裝吧。
正文zookeeper簡單介紹
既然是基於zookeeper的分布式鎖,首先肯定要對這個zookeeper有一定了解,這裡就不過多的進行講解,只對其跟分布式鎖有關聯的特性做乙個簡單的介紹,更多詳細的功能特性大家可以參閱官方文件。
zookeeper維護著類似檔案系統的資料結構,它總共有四種型別的節點
curator實現分布式鎖原理
好,當我們簡單了解了zk的節點型別以後,現在正式的分析curator分布式鎖的實現原理。這裡我們定義了乙個「/curator_lock」鎖節點用來存放相關客戶端建立的臨時順序節點。
假設兩個客戶端clienta跟clientb同時去爭奪乙個鎖,此時clienta先行一步獲得了鎖,那麼它將會在我們的zk上建立乙個「/curator_lock/***xx-0000000000」的臨時順序節點。
接著它會拿到「/curator_lock/」鎖節點下的所有子節點,因為這些節點是有序的,這時候會判斷它所建立的節點是否排在第一位(也就是序號最小),由於clienta是第乙個建立節點的的客戶端,必然是排在第一位,所以它也就拿到了鎖。
[zk: localhost:2182(connected) 4] ls /curator_lock
[_c_f3f38067-8bff-47ef-9628-e638cfaad77e-lock-0000000000]
這個時候clientb也來了,按照同樣的步驟,先是在「/curator_lock/」下建立乙個臨時順序節點「/curator_lock/***xx-0000000001」,接著也是獲得該節點下的所有子節點資訊,並比對自己生成的節點序號是否最小,由於此時序號最小的節點是clienta建立的,並且還沒釋放掉,所以clientb自己就拿不到鎖。
[zk: localhost:2182(connected) 4] ls /curator_lock
[_c_2a8198e4-2039-4a3c-8606-39c65790d637-lock-0000000001,
_c_f3f38067-8bff-47ef-9628-e638cfaad77e-lock-0000000000]
既然clientb拿不到鎖,也不會放棄,它會對自己的前乙個節點加上***(zk提供的api實現),只要監聽到前乙個節點被刪除了,也就是釋放了鎖,就會馬上重新執行獲取鎖的操作。
當後面的clientc,clientd…過來的時候也是如此,變化的只是節點上的編號,它會根據client連線的數量而不斷增加。
可能大家還會擔心,萬一我的獲取到鎖的客戶端宕機了怎麼辦,會不會不釋放鎖?其實上面已經解答了這個問題,由於curator使用的是臨時順序節點來實現的分布式鎖,只要客戶端與zk連線斷開,該節點也就消失了,相當於釋放了鎖。
下面**展示了curator的基本使用方法,僅作為參考例項,請勿在生產環境使用的這麼隨意。
curatorframework client = curatorframeworkfactory.
newclient
("127.0.0.1:2182"
,5000
,10000
,new
exponentialbackoffretry
(1000,3
)); client.
start()
; interprocessmutex interprocessmutex =
newinterprocessmutex
(client,
"/curator_lock");
//加鎖
interprocessmutex.
acquire()
;//業務邏輯
//釋放鎖
interprocessmutex.
release()
; client.
close()
;
總結
我們在搞懂了原理之後,就可以拋棄curator,自己動手實現乙個分布式鎖了,相信大家實現基本的功能都是沒問題的,但是要做到生產級別,可能還是要在細節上下功夫,比如說一些異常處理,效能優化等因素。
女朋友也能看懂的多執行緒同步
當多個執行緒同時共享同乙個全域性變數或靜態變數,做寫的操作時,可能會發生資料衝突問題,也就是執行緒安全問題。舉個案例來說 現在有100張火車票,有兩個視窗同時搶火車票,使用多執行緒模擬搶票效果。classdesc 功能描述 多執行緒之買火車票案例 展示執行緒不安全問題 class threadtra...
小白也能看懂的XML簡介
目錄 一.xml簡介 二 xml用途 三 xml結構 四 xml語法 五 xml元素 六 xml屬性 七 總結 1.xml指可擴充套件標記語言,很類似html。xml被設計為傳輸和儲存資料,其焦點是資料的內容 html被設計用來顯示資料,其焦點是資料的外觀。2.xml的設計宗旨是傳輸資料,而非顯示資...
小白也能看懂的Cookie跟Session的區別
首先為了能充分理解為什麼引入cookie和cookie是什麼,先看了例子。不然官網上定義的概念不太容易看懂。eg 我今天想找老王吃放,打 給老王 例子看完了,在看看一些官網上一些專業術語的定義。會話 由一組請求和響應組成 理解為上面例子中的 對話 是圍繞著一件相關事情 吃飯 所進行的請求和響應。這些...