文章目录

  • 1. 一致性 概览
    • 1.1 分布式系统的 “正确性”
    • 1.2 线性一致性(Linearizability)
    • 1.3 顺序一致性(Sequential consistency)
    • 1.4 因果一致性(Casual consistency)
    • 1.5 最终一致性(Eventual consistency)
  • 2. Zookeeper 的 “线性一致性” 问题
  • 3. 参考

一致性算是分布式系统的定位,一个分布式系统拥有什么样的一致性决定了它能够拥有什么样的性能。

本节从理论(设计一些分布式系统) 层面来描述不通的一致性 的要求 以及 在性能上的取舍,最后再探讨一下一致性 对于 共识算法(一致性算法) 的影响。

写这篇文章的起因 是 身边的同事 以及 接触到的分布式系统 总会引入对一致性的讨论,请教大家不通一致性的区别 以及 一致性和隔离性之间的差异时(线性一致性 和 Serializability 除了一个是一致性 一个是隔离级别,他们对请求处理上有什么差异吗) 总是从工程上得不到一个清晰的答案,所以还是自己花功夫讲这一些细节摸清楚,这样我们说一个系统拥有 “线性一致性能力”(个人已知的还没有) 以及 一个系统拥有 最终一致性 能力的时候他们的大体架构 和 性能差异都能 有一个定位框架。

1. 一致性 概览

1.1 分布式系统的 “正确性”

在分布式系统中我们想要保证系统的正确性,需要一套规则来进行约束,这一套规则就是一致性模型。

这个时候大家会想,保证正确性不是天经地义的事情吗,计算机执行 1+1 ,返回的结果一定是2呀,只要满足类似这样的正确性 不就是正确性本身的体现吗,为什么在分布式系统中需要有一套规则来描述正确性呢。

这种正确性 需要达到操作系统 寄存器级别的数据操作才行,加上CPU-cache 和 DRAM 其实就无法达到这样的正确性了。

因为cpu-cache是异步更新到DRAM的,而多线程场景,不通线程挂在不通的cpu之上,那一号线程的更新不一定立即刷到DRAM,而同时2号线程去读这块内存,可能无法读到新的数据。

很简单,我们来做一些简单的计算:

  1. 单机服务器中 CPU 距离内存大概30cm,电信号(电磁波)以接近光速的速度从CPU 传递到内存,需要1ns的时间。
  2. 分布式系统中 不通数据中心服务器之间的距离往往以百千米计,按照500km来算的话,不通服务器之间的数据传输耗时需要1.6ms。

而实际情况下,全球级别的分布式系统计算机之间的通信跨洲/跨洋 都是很普遍的,那一次请求需要几十ms以上的延时才能被其他服务器收到,相比于单机服务器几十ns到百ns的访寸或者us级别的读盘来说太长了。这个时候,一台机器写入的数据想要在另一台机器读取,显然很难保证其他机器能够读到新的数据。

所以,我们需要为分布式系统引入正确性模型,来决定当前分布式系统应该对外提现什么样的“正确性”,这个正确性可以和我们的寄存器正确性有歧义。正如,CPU的内存屏障能够为用户提供不同的一致性要求。

目前整理出来的一致性模型,从强到弱大体有以下四种(不同的论文/系统可能有自己的分类,但是较为清晰的划分有以下四种):

线性一致性(Linearizability) --> 顺序一致性(Sequential consistency) --> 因果一致性(Casual consistency) --> 最终一致性(Eventual consistency)

接下来详细看看每一种一致性的提供什么样子的正确性。

1.2 线性一致性(Linearizability)

**线性一致性 顾名思义,对于观察者来说 所有的读和写都在一条单调递增的时间线上串行推进。**整个系统对外的表现就是一个原子寄存器,能够很容易得实现CAS(compare and set)操作。

它对读写的要求是 所有的读总能返回最近的写操作的值。

优点 很明显:寄存器级别的正确性

缺点 很致命:这样的正确性 对写的要求就是 写请求需要写入到每一个服务器才算完成,中间有任何一个服务器宕机/网络分区,写都会卡住,整个系统将完全不可用。

同样的,在操作系统中,我们的CPU访存想要提供线性一致性引入的内存屏障 也会让系统性能受影响。

原本的写请求写到cpu-cache就可以返回,等待cpu-cache异步刷内存。但是现在,我们加上memory_order_seq_cst,就需要从cpu-cache同步写入到内存完成才返回。这个时候延时将从几个ns降到接近百ns。

1.3 顺序一致性(Sequential consistency)

顺序一致性则降低了线性一致性的正确性标准,不要求整个系统(分布式/单机)对外表现的读写都在一个单调递增的时间线上。顺序一致性则只需要保证一个机器上的进程处理读写请求是按照请求定义的顺序发生的即可。

要求如下:

  1. 不要求操作按照真实的时间序列发生(像下图中,读请求下发的时间在写请求之后,却可以读到这个写请求之前的数据)
  2. 不通进程间的操作执行先后顺序也没有强制要求,但必须是原子的。
  3. 单个进程内的操作顺序必须和编码时的时间顺序一致。

现在的很多分布式系统对外宣称自己是强一致性系统,其实最高的级别也就是到顺序一致性这里。包括很多人讨论的zookeeper + sync 能否提供线性一致性读 问题,其实也只能提供到顺序一致性级别(正如前面说的,操作系统在内存屏障的情况下才能保证线性一致性,实现zookeeper 时每个机器会开内存屏障?显然不可能)。

1.4 因果一致性(Casual consistency)

因果一致性要求 有**因果相关 **的操作必须按照顺序发生。比如 先发帖子,再有评论,那么发帖子的操作x 一定在评论操作y 之前发生。

因为前面的一致性模型 中对每一个操作都能用一个单一的数值表示(时间),但是在因果一致性模型中,我们会发现每一系列满足因果一致性的操作都是一个集合,我们要确保并发场景下的因果关系,就需要对两个集合进行比较。

这个一致性不要求 整个系统/整个进程 对外拥有一个特定的顺序,所以它所能够容忍的冲突更多,也就是更低的一致性要求,好处也很明显,会对性能比较友好(更高的并发处理)。

在因果一致性的系统实现中 需要捕获因果依赖关系,这个操作在数据库系统中会引入一些计算/存储代价,间接增加了系统的复杂度。
业界很少有因果一致性的系统,虽然其能够允许更高的并发,但是引入的额外复杂度会影响大家的选择。 后续的文章会介绍因果一致性系统的经典实现COPS。

1.5 最终一致性(Eventual consistency)

这里就不多说了,系统不会限制用户的任何操作方式,允许每个原子操作的顺序执行任意的重排。

在某一时刻,会保证能够读到对数据的更新,(某一时刻。。。这里可以算做是一个量子的混合态,不论什么时候,对外的表现就是只有用户读了,可能才会写入成功 or 没有成功,也就是写入的时机取决于用户什么时候读取,哈哈,是不是很有趣)。

2. Zookeeper 的 “线性一致性” 问题

很多网上的文章会说zookeeper 这个分布式协调系统能够提供线性一致性的模型。

我们先不评论说的正确与否,先看看 线性一致性的定义:所有的读操作总能够返回最新写入的值。这个一致性应用到整个zookeeper的分布式系统中来看,也就是 1 号客户端的写入完成,从 2 号客户端立即读,就能读到这个写入的值。

(1)首先,zookeeper是一写,多读,写操作都会交给leader进行,读操作leader-follower都可以处理。那我们把2号客户端的读请求放在follower,也就是说follower要能够实时读到leader写入的数据。这里就需要知道在 zookeeper 的 ZAB 的 Broadcast 阶段,为了实现zookeeper 的性能,leader本地的请求commit 是会按照zxid进行,但是远端follower的的commit 则是异步的(zookeeper论文描述的是A-Linearizability),leader发送commit请求的时候会同时向客户端 返回写入成功,异步向follower发送commit请求。这个时候客户端收到的写入成功并不能代表follower写入成功,所以从follower 读是读不到最新的写入的。

(2)其次,大家会说用sync+read 就可以呀。也就是每一个写/更新 操作都携带sync, 那我们是不是就可以保证读的线性一致性了。。。先看看sync 操作的定义,ZAB 论文中这样描述:

也就是说在BroadCast 阶段,对集群的update/写操作都会交给leader处理,这个时候让leader 携带sync操作,leader会让这一些更新/写 操作同步到所有的follower 才返回。

听起来好像是这么回事哈,写/更新 操作成功了,之后的从follower读肯定都能读到最新的值了,当然,集群正常情况下(且操作在每一个机器加上内存屏障),从一致性的语义来看,线性一致性读满足了的。然而, 分布式系统我们主体讨论的则是集群异常情况下的一致性表现。

a. 关于sync+read 是否满足线性一致性读问题,先看一下jepsen 对zookeeper 测试过程的一个讨论

场景大概是这样的:

正常情况下的集群如下

一写多读,多个链接到集群的客户端的写/更新操作会被转发给leader 处理,读请求可以被任何follower处理,sync+read 能够让follower读到leader最新接收到的写入。

但是,当集群发生网络分区的时候:

之前的leader因为没有办法满足majority,无法成为leader,且写请求会被阻塞。另一边之前的三个follower 因为能够满足majority,则可以重新选举出来一个leader ,从而能够接受写请求。在分区发生的之前可能会出现leader本地已经写入了,但是在同步到远端写入的时候刚好分区,远端的follower写入没有成功。这个时候,远端是三个节点的新集群中其实并没有最新的写入,也就无法满足线性一致性读了。

b. 关于sync+read 是否满足线性一致性读问题,从 分布式学习交流群中 看到有小伙伴描述了这样一个场景:

先看场景,就是说不同的客户端想要保证“自己的线性一致性”,他们更新的数据他们希望能够读到,但是更新到读这个过程被其他的客户端更新了,那这个小伙伴认为就不是线性一致性了。

当然,从线性一致性个的语义来看,这个场景并不是线性一致性的场景。线性一致性模型是对整个系统而言的,A 客户端被 B客户端的请求覆盖,然后A读到了B的更新数据,这本身就是整个系统的线性一致性的语义。关于说 A的线性一致性读。。。其实是描述有问题的。。。

还是回到前面 关于zookeeper的线性一致性讨论中,那很明显,在集群异常的情况下,即使有sync操作 , zookeeper也是无法保证严格的线性一致性的语义的。

3. 参考

1. zookeeper paper
2. ZAB paper
3. https://github.com/jepsen-io/jepsen/issues/399
4. https://aphyr.com/posts/291-jepsen-zookeeper
5. https://aphyr.com/posts/313-strong-consistency-models#comment-2578

分布式系统 一致性模型的介绍 以及 zookeeper的 “线性一致性“ 讨论相关推荐

  1. 分布式系统:一致性模型

    分布式系统中一个重要的问题就是数据复制,数据复制一般是为了增强系统的可用性或提高性能.而实现数据复制的一个主要难题就是保持各个副本的一致性.本文首先讨论数据复制的场景中一致性模型如此重要的原因,然后讨 ...

  2. 分布式系统概念:一致性协议、一致性模型、拜占庭问题、租约、副本协议

    1,一致性协议 两阶段提交协议与Raft协议.Paxos协议 ①两阶段提交协议 在分布式系统中,每个节点虽然可以知晓自己的操作时成功或者失败,却无法知道其他节点的操作的成功或失败.当一个事务跨越多个节 ...

  3. 深入浅析zookeeper的一致性模型及其实现

    现在我们来考察一下zookeeper的一致性模型. 常见误区 一开始看到网上有人说zookeeper满足了CAP的CP特性,我一直以为zookeeper至少也是Sequential Consisten ...

  4. 分布式系统中的一致性模型

    文章目录 什么是一致性模型? 强一致性模型 线性一致性(Linearizable Consistency) 顺序一致性(Sequential Consistency) 弱一致性模型 因果一致性(Cau ...

  5. 从Paxos到Zookeeper:分布式一致性原理与实践

    网站 更多书籍点击进入>> CiCi岛 下载 电子版仅供预览及学习交流使用,下载后请24小时内删除,支持正版,喜欢的请购买正版书籍 电子书下载(皮皮云盘-点击"普通下载" ...

  6. 聊一聊ZooKeeper的顺序一致性

    来自:架构之美 ZooKeeper作为分布式应用系统协调服务,在分布式系统中的应用非常广泛,在某些业务场景下甚至可以作为注册中心.分布式锁来使用.ZooKeeper之所以能有如此广泛的应用,与它良好的 ...

  7. 聊聊高并发(三十三)Java内存模型那些事(一)从一致性(Consistency)的角度理解Java内存模型

    可以说并发系统要解决的最核心问题之一就是一致性的问题,关于一致性的研究已经有几十年了,有大量的理论,算法支持.这篇说说一致性这个主题一些经常提到的概念,理清Java内存模型在其中的位置. 一致性问题更 ...

  8. 《从Paxos到Zookeeper:分布式一致性原理与实践》第一章读书笔记

    第一章主要介绍了计算机系统从集中式向分布式系统演变过程中面临的挑战,并简要介绍了ACID.CAP和BASE等经典分布式理论,主要包含以下内容: 集中式的特点 分布式的特点 分布式环境的各种问题 ACI ...

  9. python django框架分析_Django框架模型简单介绍与使用分析

    本文实例讲述了Django框架模型简单介绍与使用.分享给大家供大家参考,具体如下: ORM介绍 ORM Object relational mapping 对象关系映射 把面向对象中的类和数据库表一一 ...

最新文章

  1. android:intent flags
  2. (一) 自带刷新的列表-LtRecyclerView v2.x版本(LtAdapter)(基本使用)
  3. 使用css3制作正方形、三角形、扇形和饼状图
  4. 【Python】字符转换为 ASCII 码
  5. w3c dom操作Xml时从加入另一个XML文件的一个元素
  6. 软件开发中 前台、中台、后台英文_最近处处惹人爱的中台到底是什么
  7. 音视频开发(17)---RTSP再学习 -- 利用FFmpeg 将 rtsp 获取H264裸流并保存到文件中
  8. python连载第11篇 if 语句
  9. 创业,白手起家需要些什么?
  10. TDX抢反弹指标(不含未來函数)
  11. 网络安全之***手法计中计
  12. OBIEE-----ClusterControler通信的问题
  13. 【C++】指针遍历二维数组若干种方法小结
  14. Struts2 简单的上传文件并且显示图片
  15. 小米4C关闭html查看器,小米4C解锁教程_小米4C一键解锁Bootloader的方法
  16. 彻底清除 mplay.com与mplay.exe病毒
  17. 英语的句号在c语言中是什么意思,英语标点符号的用法
  18. 浏览器的邮件html编辑器无效,eWebEditor 辑器按钮失效 IE8下eWebEditor编辑器无法使用的解决方法...
  19. Laravel - 从百草园到三味书屋 From Apprentice To Artisan目录
  20. 同济大学核心学术刊物基本目录_党建丨清华大学建筑学院、同济大学建筑与城市规划学院研究生党支部联合举办“城乡二元关系与生态文明建设内涵”主题党日活动...

热门文章

  1. eclipse导入lombok后打不开(如果你的lombok不是最新的,那就来下载最新的)
  2. Android采用Application总结一下
  3. 位域 内存 字节序_JS操作内存?二进制数组了解一下
  4. OpenCV+python:膨胀和腐蚀
  5. 萨默尔机器人_沣东新城王寺街道《民法典》企业宣传活动走进西安萨默尔科技...
  6. 如何判断第一位是1_如何快速判断1瓶红酒的价格,防止被坑?
  7. 显微镜下的大明内容_《显微镜下的大明》epub、mobi、azw3
  8. 的内怎么放_冰箱不是“万能”箱,哪些食物不宜放冰箱储存?
  9. 化工学python_化工计算与软件应用(第2版) PDF
  10. python默认的一个代码缩进是几个空格_python缩进长度是否统一