大数据分布式基础-Lease机制简介和应用

Lease机制简介

   lease中文叫租约,是一种广泛应用于分布式系统领域的协议,它是一种维护分布式系统一致性的有效工具

    lease通常定义为:颁发者在一定期限内给予持有者一定权利的协议。

    Lease 表达了颁发者在一定期限内的承诺,只要未过期颁发者必须严格遵守 lease 约定的承诺。

    Lease 的持有者在期限内使用颁发者的承诺,但 lease 一旦过期必须放弃使用或者重新和颁发者续约。


背景和介绍


           缓存是计算机里广泛使用的一种技术,对降低读取延迟、网络流量和服务器负载都非常有效,但也带来了一致性(Consistency)的问题。所谓一致就是客户端总能读到最新的数据,使用缓存后有可能服务器端的数据已经被修改,但客户端仍然从缓存中读取陈旧的数据。为了保证一致性,有两种常见的解决办法,第一种是轮询(Polling),即每次读取数据时都先询问服务器数据是不是最新的,如果不是就从服务器传输新数据,这种方法需要每次读取数据时都与服务器通信。另一种方法就是回调(Callback),就是由服务器记住有哪些客户端读取了数据,对数据做修改时首先通知所有这些客户端数据已经失效,这种方法的问题在于服务器需要记住所有读取过数据的客户端,这是很大的负担,更严重的是,一旦有客户端联系不上或者丢失了客户端的信息,修改操作就无法继续。

       1989年斯坦福大学的Cary G. Gray和David R. Cheriton提出了利用租约来维护缓存一致性的方法。所谓租约,其实就是一个合同,即服务器给予客户端在一定期限内可以控制修改操作的 权力。如果服务器要修改数据,首先要征求拥有这块数据的租约的客户端的同意,之后才可以修改。客户端从服务器读取数据时往往就同时获取租约,在租约期限内,如果没有收到服务器的修改请求,就可以保证当前缓存中的内容就是最新的。如果在租约期限内收到了修改数据的请求并且同意了,就需要清空缓存。在租约过期以后,客户端如果还要从缓存读取数据,就必须重新获取租约,我们称这个操作为“续约”。

       在租约期限内,客户端可以保证其缓存中的数据是最新的。同时,租约可以容忍各种非拜占庭式失效(机器崩溃、网络分割等)。如果客户端崩溃或者网络中断,服务器只需要等待其租约过期就可以进行修改操作。如果服务器出错丢失了所有客户端的信息,它只需要知道租约的最长期限,就可以在这个期限之后安全的修改数据。与回调方式相比,服务器只需记住还拥有租约的客户端即可。

      租约与带期限的锁非常相似,但更加灵活,因为租约还提供了“寻求同意”的机制(我觉得可以称为“带期限可妥协的锁”)。服务器还可以实现多种租约,比如“写租约”和“读租约”,并保证一个时间段内只有一个写租约或者多个读租约,这就相当于是单写者多读者的锁协议。

      因为租约是基于时间的,因此其有效性需要系统时间来保证。如果服务器的时钟快而客户端时钟慢,那么有可能服务器认为一个租约已经过期而客户端仍然认为其有 效,就可能导致错误。对这种情况就必须通过时钟同步协议来解决了,不过这种情况很少见。一般情况下,我们可以认为一个分布式系统的时间是同步在一个很小的时间差e之内,只需把这个e考虑到租约期限内即可。


租约的应用


1:动态秘钥管理

      中心密钥服务器维护着全局的密钥生成和发放,所有需要使用密钥的外围系统向密钥服务器申请密钥用于本系统的加解密工作。出于性能和可用性考虑,不能每个请求都向中心服务器去申请,因此密钥通常被缓存在本地系统中。那么当需要修改中心系统的密钥时(出于安全性考虑的定期修改),如何保证所有使用该密钥的本地系统都立刻丢弃过期的密钥,而立刻向中心密钥服务器重新申请最新的密钥,并保持所有系统中密钥的一致性?

       这个场景非常适合用lease机制来解决,中心服务器发放密钥的时候,同时发放一个 lease 承诺在一定时间内不修改该密钥。本地系统获取密钥时,同时根据 lease 的约定只在其有效期内使用密钥,lease 一旦过期立刻重新申请密钥。当变更密钥时,在所有已颁发的 lease 全部过期前修改不能生效,并且在变更密钥生效期间不能颁发新的 lease,避免形成活锁(永远等不到所有 lease 失效)。


2:分布式文件系统

     以hadoop的hdfs为例,每个文件块都有多个副本分布在多个slave上,在 并行追加时必须有一个全局统一的追加顺序。当然这个顺序可以由master来确定,但是这样会大大增加master的负荷。另一种方法可以由多个 slave通过一致性协议(比如Paxos)来达成一个一致,但这样开销太大。hdfs使用了租约机制,就是对每个文件块,由master向一 个slave发放租约,在租约期限内就由它来负责并行追加操作的顺序。slave正常运行时可以一直续约,如果出现了机器失效或 者网络分割的情况,master就在租约过期以后把租约交给另外一个slave。在某些情况下,master也会联系拥有租约的 slave,请它们提前释放租约。

    

3:状态检测

       在通常的集群系统中,我们采用心跳来检测节点状态。但普通的心跳机制是无协议和承诺约定的,所以它的检测结果可能不可靠。很多监控系统采用心跳检测集群中节点的存活性,这种机制存在误报警的可能。

       普通心跳通常是在规定的时限内定期向检测节点发送存活性报告,若超出一段时间未能收到心跳报告,那么检测节点则判断节点可能失效,并采取一系列措施(报警、通知节点的使用者)。这种机制存在的问题是,检测节点单方面判定节点失效,在某些业务集群系统中可能存在风险。节点自身并未认识自己已被认定失效,还在继续提供正常的服务。若该节点在集群中承担唯一 primary 节点的职责,而检测节点的失效判定发起了重新选择新的主节点,会引发“双主”问题。

       采用 lease 机制的心跳实现,则彻底避免了此类问题。由于网络分割的原因,其实没有任何技术可以可靠的判定节点状态,但采用 lease 机制的状态检测,可以避免出现误判时引入新的问题。


租约总结:

       在很多时候,租约的定义似乎很模糊,有的时候租约类似心跳,有的时候又类似于锁。到底租约的本质是什么呢?
      回到租约最原始的定义:租约就是在一定期限内给予持有者特定权力的协议。我觉得这里的期限就是租约的根本特性,正是这一特性使得租约可以容忍机器失效和网络分割。在期限之内,租约其实就是服务器和客户端之间的协议,而这个协议的内容可以五花八门。

    1:如果协议内容是服务器确认客户端还存活,那么这个租约的功能就相当于心跳

    2:如果协议内容是服务器保证内容不会被修改,那么这个 租约就相当于读锁

    3:如果协议内容是服务器保证内容只能被这个客户端修改,那么这个租约就相当于写锁

    租约这种灵活性和容错性,使其成为了维护分布式系统一致性的有效工具。




    


 

你可能感兴趣的:(大数据分布式基础)