了解分布式一致性的一些概念和理论,介绍简单常用的分布式一致性协议。主要介绍二阶段提交和三阶段提交的基本流程,并相互比较。
通常可以吧一系列的分布式的操作序列称之为子事务。分布式事务也可以被定义为一种嵌套型事物。分布式系统不可能像单机系统那样可以严格满足 ACID 特性,所以要有不同的取舍,因此有了 CAP 和 BASE 理论。
一个分布式系统不可能同时满足 一致性(C:Consistency) 、 可用性(A:Availability) 和 分区容错性(P:Partition tolerance) 这三个基本需求。
一致性:在分布式环境中,一致性是指数据在多个副本之间是否能够保持一致的特性。数据在发生变化的时候,需要保证发生变化之后,所有的副本都能保持一致。
可用性:系统提供的服务必须一直处于可运送的状态,对于每一个请求总是能够在有限的时间内返回结果。
分区容错性:分布式系统在遇到任何网络分区故障的时候,仍然需要保证对外提供满足一致性和可用性的服务。
对于 CAP 的取舍:放弃 P 的通用做法是将所有的数据都放到一个节点,这样可以避免网络分区带来的问题,但是值得注意的是, 放弃了 P 也就等于放弃了系统的扩展性 ;放弃 A :当系统发生故障的时候,允许系统短时间内不可用,需要等待系统恢复后方可继续提供服务; 放弃 C: 放弃 C 并不是说放弃最终一致性 ,而是说放弃强一致性,保证系统在某段时间之后能够达到最终一致性。
对于一个分布式系统而言,不同节点之间必然存在网络通讯,因此网络分区问题是不可避免的。同时分布式系统的扩展特性也是无法舍弃的。 因此系统的设计和架构一般都考虑如何权衡 A 和 C。
BASE 是 Basically Available(基本可用)、Soft status(软状态)和 Eventually consistent(最终一致性)三个短语的缩写。
基本可用:在系统出现故障的时候,允许损失部分可用性。比如响应时间上的损失和功能上的损失。
软状态:也称为弱状态,表示允许系统中的数据存在中间状态,即允许不同的数据副本之间数据同步存在延迟。
最终一致性:经过一段时间的同步之后,系统最终能够达到一个数据一致的状态。
最终一致性的一些变种:
当一个事务需要跨越多个分布式节点的时候,需要引入一个成为 “协调者”(Coordinator) 的组件来统一调度所有分布式节点的执行逻辑,这些被调度的分布式节点则被称为 “参与者”(Participant) 。协调者负责调度参与者的行为,并最终决定这些参与者是否真的需要把事务进行真正的提交。由此,衍生出二阶段提交和三阶段提交两种协议。
两阶段提交主要包含 投票(Propose) 和 执行(Commit) 两个阶段。
在 Propose 阶段,协调者向所有参与者(voter)发送事务内容,询问是否可以执行事务提交操作,并等待参与者的响应。各个参与者为该事务预留资源,保证在下一个阶段能够提交事务,如果资源可以获取反馈给协调者 agree 响应,反之返回 disagree 响应。
事务提交:如果在 Propose 阶段,所有参与者都返回的是 agree 信号,那么协调者会发送提交事务的请求;所有参与者收到事务提交请求后会正式执行事务提交操作并释放事务执行期间占用的资源,执行完成后将事务执行结果反馈给协调者;协调者收到所有参与者的反馈信息后,事务执行完毕。
事务中断:如果在 Propose 阶段有参与者返回 disagree 或者有的节点超时未返回,没有投票达成一致,那么协调者会向所有参与者发送回滚请求;参与者收到回滚请求之后会释放掉在 Propose 阶段占用的资源,然后反馈信号给协调者;协调者收到反馈消息之后,完成事务终端。
二阶段提交协议的优点是:原理简单,实现方便。
二阶段提交协议的缺点是:
假设coordinator和voter3都在Commit这个阶段crash了, 而voter1和voter2没有收到commit消息. 这时候voter1和voter2就陷入了一个困境. 因为他们并不能判断现在是两个场景中的哪一种:
三阶段提交是在二阶段提交的基础上进行的改进,将二阶段提交的 Propose Phase 一分为二,形成了 CanCommit、PreCommit 和 doCommit 三个阶段。
CanCommit:协调者向所有参与者询问是否可以执行事务提交操作;各参与者想协调者反馈是否可以提交事务。
需要注意的是,在 doCommit 阶段,可能出现下面的两种故障:
无论出现上面那种情况,都会造成从黁税额无法及时收到来自协调者的 doCommit 请求或者是 abort 请求,针对这种情况,参与者会在等待超时之后,继续事务的提交操作。
二阶段提交协议的优点是:相比于 2PC 能够在单点故障后继续达成一致。
二阶段提交协议的缺点是:引入了新的问题,如果某个参与者与协调者出现在不同的网络分区,那么该参与者会提交事务,有可能出现数据不一致的情况。
我来评几句
登录后评论已发表评论数()