日韩性视频-久久久蜜桃-www中文字幕-在线中文字幕av-亚洲欧美一区二区三区四区-撸久久-香蕉视频一区-久久无码精品丰满人妻-国产高潮av-激情福利社-日韩av网址大全-国产精品久久999-日本五十路在线-性欧美在线-久久99精品波多结衣一区-男女午夜免费视频-黑人极品ⅴideos精品欧美棵-人人妻人人澡人人爽精品欧美一区-日韩一区在线看-欧美a级在线免费观看

歡迎訪問 生活随笔!

生活随笔

當前位置: 首頁 > 编程资源 > 编程问答 >内容正文

编程问答

Zookeeper实践与应用--分布式锁实现

發布時間:2023/12/4 编程问答 30 豆豆
生活随笔 收集整理的這篇文章主要介紹了 Zookeeper实践与应用--分布式锁实现 小編覺得挺不錯的,現在分享給大家,幫大家做個參考.

分布式鎖

  • 分布式鎖是控制分布式系統之間同步訪問資源的一種方式,如果不同系統是同一個系統的不同主機之間共享一個或一組資源,那么訪問這些資源的時候,往往需要通過一些呼哧手段來防止彼此之間的干擾保證統一性,因此需要分布式鎖。
排他鎖
  • 簡稱X鎖,或寫鎖,獨占鎖,是一種基本的鎖類型,如果事務T1對數據對象Q1加上排他鎖,那么整個加鎖期間,只允許事務T1對Q1進行讀,寫操作,其他任何事務不能對Q1操作,直到T1釋放
定義鎖
  • Java開發中有兩種方式,synchronized機制和JDK5中的ReentrantLock,然而,在Zookeeper中,沒有類似于這樣的API可以使用,Zookeeper通過數據節點表示一個鎖,例如/exclusive_lock/lock節點被定義位一個鎖
獲取鎖
  • 獲取排他鎖時,所有客戶端調用create接口在/exclusive_lock節點下創建臨時子節點/exclusive_lock/lock,Zookeeper保證只有一個客戶端創建成功,我們認為這個創建成功的客戶端就獲取到鎖,其他客戶端需要在/exclusive_lock/lock節點上注冊一個watcher監聽,以便實時監聽Lock節點變化
釋放鎖
  • /exclusive_lock/lock是一個臨時節點,以下兩種情況可認為釋放
    • 當前獲取鎖的客戶端機器宕機,ZooKeeper上的臨時節點會被自動移除
    • 正常執行業務邏輯后,客戶端自行刪除臨時節點
  • 無論上面兩種哪一種,Zookeeper刪除臨時節點后/exclusive_lock/lock上注冊Watcher監聽的客戶端都會收到Watcher通知,再次重新發起分布式鎖的獲取,重復以上流程,如下圖所示排他鎖流程
共享鎖
  • 共享鎖簡稱S鎖,又稱為讀鎖,同樣是一種基本鎖,如果T1對Q1加上共享鎖,那么當前事務只能多Q1進行讀,其他事務也只能對這個數據加共享鎖,直到所有共享鎖都釋放。下面借助ZooKeeper來實現共享鎖
定義鎖
  • 與排他鎖一樣,同樣通過ZooKeeper節點表示鎖,類似/shared_lock/[Hostname]-請求類型-序號,的臨時順序節點,例如/shared_lock/129.168.1.1-R-0000001那么這個代表一個共享鎖
獲取鎖
  • 客戶端到/shared_lock這個節點下創建一個臨時順序節點,如果當前是讀請求,那么就叉棍就如/shared_lock/129.168.1.1-R-0000001的節點,如果是寫/shared_lock/129.168.1.1-W-0000001
判斷讀寫順序
  • 根據共享鎖定義,不同事務可以同一時間多一個數據讀,而更新只能單獨進行,我們通過Zoo keep如下方式來進行:
  • 創建節點后,獲取/shared_lock節點下的所有子節點,并對該節點注冊子節點變化的Watcher監聽
  • 確定字節節點序號在所有子節點中順序
  • 對于讀請求:如果沒有比字節序號小的子節點,或者是所有比字節序號小的子節點都是讀,表明字節已經成功獲取共享鎖,同時開始讀
  • 對于寫請求:如果子不是序號最小的子節點,進入等待
  • 接收Watcher后,重復步驟1
釋放鎖
  • 與排他鎖一致,刪除釋放
  • 用如下圖解釋
羊群效應
  • 在規模不大,10臺機器作業,上面方案能有很高的效率,如果規模變大,會存如下的這種問題,在判斷讀寫順序的時候,會給子節點列表添加watcher監聽,這樣任何一個子節點修改都會有watcher通知信息,如下圖:
  • 192.168.0.1 這條機器首先進行讀,然后刪除節點
  • 余下四臺機器都能收到子節點移除通知,然后從/shared_lock節點上獲取一份新子節點列表
  • 每個機器判斷自己讀寫順序,其中192。168.0.2這臺機器檢測自己是最小序號,開始寫操作,余下繼續等待
  • 繼續2 步驟
    • 上面操作是共享鎖實現主要步驟,當任意一個子節點變化后,Watcher通知會給所有其他集群通知,然而現實是這個通知其實只對192.168.0.2這個機器有用,對其他節點來說無任何作用。
    • 后果: 分布式競爭中,滿天飛的無效watcher通知,和無效的子節點獲取,然后進行等待,無意義的操作會消耗非常多的系統性能,對Zookeeper服務器造成巨大性能影響和網絡沖擊,更嚴重的是如果同一時間有多個節點對應的客戶端完成事務或是事務中斷引起節點變化,Zookeeper需要在短時間內向其余客戶端發送大量事件通知—這就是羊群效應。
    改進后的分布式鎖實現
    • 主要改動:每個競爭者,只需關注/shared_lock節點下序號比自己小的節點是否存在即可:
  • 客戶端create創建"類似/shared_lock/[Hostname]-請求類型-序號" 的臨時節點
  • 客戶端調用getChildren接口獲取所有已經創建子節點列表(不注冊watcher)
  • 如果無法獲取共享鎖,調用exist對比比自己小的節點注冊watcher(id比自己小,可用時間戳)
  • 讀請求:向比自己序號小的最后一個寫請求節點注冊watcher監聽
  • 寫請求:向比自己序號小的最后一個節點注冊watcher監聽
  • 等待watcher通知,繼續2 步驟
    • 如下圖:
    注意
    • 并不是一定每次都用改進后的,因為改進版本流程復雜,如同我們在多線程并發編程中會盡量縮小鎖的范圍,對分布式鎖的實現改進也是這樣的思路,對開發時候來說,應該具體情況具體分析:集群規模不大,網絡資源豐富,第一張分布式鎖簡單,如果集群達到一定程度,希望能精細化處理分布式鎖,可以用第二種分布式鎖實現。

    上一篇Zookeeper實踐與應用-- Nginx負載均衡差異
    下一篇Zookeepe實踐與應用–分布隊列

    總結

    以上是生活随笔為你收集整理的Zookeeper实践与应用--分布式锁实现的全部內容,希望文章能夠幫你解決所遇到的問題。

    如果覺得生活随笔網站內容還不錯,歡迎將生活随笔推薦給好友。