如何用Zookeeper来实现分布式锁?
什么是Zookeeper临时顺序节点?
例如 :
/
动物 植物
猫 仓鼠 荷花 松树
Zookeeper的数据存储结构就像一棵树,这棵树由节点组成,这种节点叫做Zonde.
# Znode分为四种类型 :
1.持久节点(PERSISTENT)
默认的节点类型.创建节点的客户端与zookeeper断开连接后,该节点依旧存在.
2.持久节点顺序节点(PERSISTENT_SEQUENTIAL)
所谓顺序节点,就是在创建节点时,Zookeeper根据创建的时间顺序给该节点名称进行编号.
例如 :
仓鼠
仓鼠0001 仓鼠0002 仓鼠0003
3.临时节点(EPHEMERAL)
和持久节点相反,当创建节点的客户端与zookeeper断开连接后,临时节点会被删除 :
4.临时顺序节点(EPHEMERAL_SEQUENTIAL)
临时顺序节点结合了临时节点和顺序节点的特点 : 在创建节点时,Zookeeper根据创建的时间顺序给该节点名称进行编号 ; 当创建节点的客户端与zookeeper
断开连接后,临时节点会被删除.
# Zookeeper分布式锁的原理
Zookeeper分布式锁恰恰应用了临时顺序节点
## 获取锁 :
首先,在Zookeeper当中创建一个持久节点ParentLock.当第一个客户端想要获得锁时,需要在ParentLock这个节点下面创建一个临时顺序节点Lock1.
之后,Client1查找ParentLock下面所有的临时顺序节点并排序,判断自己所创建的节点Lock1是不是顺序最靠前的一个.如果是第一个节点,则成功获得锁.
这时候,如果再有一个客户端Client2前来获取锁,则在ParentLock下再创建一个临时顺序节点Lock2.
Client2查找ParentLock下面所有的临时顺序节点并排序,判断自己所创建的节点Lock2是不是顺序最靠前的一个,结果发现节点Lock2并不是最小的.
于是,Client2向排序仅比它靠前的节点Lock2注册Watcher,用于监听Lock1节点是否存在.这意味着Client2抢锁失败,进入了等待状态.
这时候,如果又有一个客户端Client3前来获取锁,则在ParentLock下再创建一个临时顺序节点Lock3.
Client3查找ParentLock下面所有的临时顺序节点并排序,判断自己所创建的节点Lock3是不是顺序最靠前的一个,结果同样发现节点Lock3并不是最小的.
于是,Client3向排序仅比它靠前的节点Lock2注册Watcher,用于监听Lock2节点是否存在.这意味着Client3同样抢锁失败,进入了等待状态.
这样一来,Client1得到了锁,Client2监听了Lock1,Client3监听了Lock2.这恰恰形成了一个等待队列,很像是Java当中的ReentrantLock所依赖的AQS(AbstractQueuedSynchronizer)
## 释放锁 :
释放锁分为两种情况 :
1.任务完成,客户端显示释放
当任务完成时,Client1会显示调用删除节点Lock1的指令.
2.任务执行过程中,客户端崩溃
获得锁的Client1在任务执行过程中,如果Duang的一声崩溃则会断开与Zookeeper服务端的链接.根据临时节点的特性,相关联的节点Lock1会随之自动删除.
由于Client2一直监听着Lock1的存在状态,当Lock1节点被删除,Client2会立刻收到通知.这时候Client2会再次查询ParentLock下面的所有节点,确认自己创建
的节点Lock2是不是目前最小的节点.如果是最小,则Client2顺利成章获得锁.
同理,如果Client2也因为任务完成或者节点崩溃而删除了节点Lock2,那么Client3就会接到通知.最终,Client3成功得到了锁.
Zookeeper和Redis分布式锁的比较
Zookeeper的
优点 :
1.有封装好的框架,容易实现.
2.有等待锁的队列,大大提升抢锁效率.
缺点 :
1.添加和删除节点性能较低.
Redis
优点 : Set和Del指令的性能较高.
缺点 :
1.实现复杂,需要考虑超时,原子性,误删等情形.
2.没有等待锁的队列,只能在客户端自旋等锁,效率低下.
两者都可以在客户端实现可重入逻辑.
在Apache的开源框架Apache Curator中,包含了对Zookeeper分布式锁的实现,源码 : https://github.com/apache/curator/
如何用Zookeeper来实现分布式锁?的更多相关文章
- 基于zookeeper实现的分布式锁
基于zookeeper实现的分布式锁 2011-01-27 • 技术 • 7 条评论 • jiacheo •14,941 阅读 A distributed lock base on zookeeper ...
- java使用zookeeper实现的分布式锁示例
java使用zookeeper实现的分布式锁示例 作者: 字体:[增加 减小] 类型:转载 时间:2014-05-07我要评论 这篇文章主要介绍了java使用zookeeper实现的分布式锁示例,需要 ...
- ZooKeeper 笔记(6) 分布式锁
目前分布式锁,比较成熟.主流的方案有基于redis及基于zookeeper的二种方案. 大体来讲,基于redis的分布式锁核心指令为SETNX,即如果目标key存在,写入缓存失败返回0,反之如果目标k ...
- 基于Zookeeper实现多进程分布式锁
一.zookeeper简介及基本操作 Zookeeper 并不是用来专门存储数据的,它的作用主要是用来维护和监控你存储的数据的状态变化.当对目录节点监控状态打开时,一旦目录节点的状态发生变化,Watc ...
- 利用ZooKeeper简单实现分布式锁
1.分布式锁的由来: 在程序开发过程中不得不考虑的就是并发问题.在java中对于同一个jvm而言,jdk已经提供了lock和同步等.但是在分布式情况下,往往存在多个进程对一些资源产生竞争关系,而这些进 ...
- 基于zookeeper简单实现分布式锁
https://blog.csdn.net/desilting/article/details/41280869 这里利用zookeeper的EPHEMERAL_SEQUENTIAL类型节点及watc ...
- 基于zookeeper实现高性能分布式锁
实现原理:利用zookeeper的持久性节点和Watcher机制 具体步骤: 1.创建持久性节点 zkLock 2.在此父节点下创建子节点列表,name按顺序定义 3.Java程序获取该节点下的所有顺 ...
- zookeeper实现的分布式锁
在分布式系统中,多个jvm对共享资源进行操作时候,要加上锁,这就是分布式锁 利用zookeeper的临时节点的特性,可以实现分布式锁 public class ZookeeperDistrbuteLo ...
- 如何用redis正确实现分布式锁?
先把结论抛出来:redis无法正确实现分布式锁!即使是redis单节点也不行!redis的所谓分布式锁无法用在对锁要求严格的场景下,比如:同一个时间点只能有一个客户端获取锁. 首先来看下单节点下一般r ...
随机推荐
- [leetcode] database解题记录
175 Combine Two Tables 题目:左连接Person表和Address表. select FirstName,LastName,City,State from Person p le ...
- 【前端JS】radio 可单选可点击取消选中
普通情况下 radio 单选框仅仅能实现多选一的效果,可是一旦选择当中一个后,这个单选框就不可点击取消其选中状态了.这样的功能在某些业务环境下并不适用.有时我们既须要单选框的多选一效果.也须要复选框的 ...
- Golang 现有的哲学中,要求你尽量手工处理所有的错误返回
更优雅的 Golang 错误处理 - Go语言中文网 - Golang中文社区 https://studygolang.com/articles/9407
- Javascript正则中的exec和match
分几种情况说明 1.假设re中不是全局的也就是不带g var str = "cat3 hat4"; var re = /\w+\d/; var ex = re.exec(str); ...
- Vijos 1921 严厉的班长 【状态压缩动态规划】
严厉的班长 描述 木姑娘在班级里面是班长.虽然是副班长,却有着比正班长更高的威信,并深受小朋友们的爱戴. 每天眼保健操时间,木姑娘都要监督所有小朋友认真做眼保健操.整个过程被描述为n个时间段,第i个时 ...
- About "self"
Class method can't refer derectly to instance variables. Within the body of a class method, self re ...
- mysql字符串的常用函数(截取和拼接)
#截取字符串(先正序取2个,再倒序取1个)SELECT SUBSTRING_INDEX(SUBSTRING_INDEX('aaa-gg-cc-dd','-',2),'-',-1) #获取子表某个字段的 ...
- 内核添加dts后,device和device_driver的match匹配的变动:通过compatible属性进行匹配【转】
本文转载自:http://blog.csdn.net/ruanjianruanjianruan/article/details/61622053 内核添加dts后,device和device_driv ...
- MYSQL初级学习笔记一:MYSQL常用命令和数据库操作(DDL)!(视频序号:初级_3,4)
知识点一:MYSQL常用命令(3) 登入方法:一,mysql –u 账号 –p 密码 退出方法:一,EXIT,QUIT 修改MYSQL命令提示符: 连接上客户机之后,通常使用prompt命令修改: 连 ...
- poj 1094 Sorting It All Out 解题报告
题目链接:http://poj.org/problem?id=1094 题目意思:给出 n 个待排序的字母 和 m 种关系,问需要读到第 几 行可以确定这些字母的排列顺序或者有矛盾的地方,又或者虽然具 ...