CAP原则介绍
CAP原则又称CAP定理,指的是在一个分布式系统中,一致性(Consistency)、可用性(Availability)、分区容错性(Partition tolerance)。CAP 原则指的是,这三个要素最多只能同时实现两点,不可能三者兼顾。
CAP的三个指标
一致性(Consistency)
“all nodes see the same data at the same time”,即更新操作成功并返回客户端后,所有节点在同一时间的数据完全一致,这就是分布式的一致性。一致性的问题在并发系统中不可避免,对于客户端来说,一致性指的是并发访问时更新过的数据如何获取的问题。从服务端来看,则是更新如何复制分布到整个系统,以保证数据最终一致
可用性(Availability)
可用性指“Reads and writes always succeed”,即服务一直可用,而且是正常响应时间。好的可用性主要是指系统能够很好的为用户服务,不出现用户操作失败或者访问超时等用户体验不好的情况。
分区容错性(Partition tolerance)
即分布式系统在遇到某节点或网络分区故障的时候,仍然能够对外提供满足一致性或可用性的服务。
CAP定理的证明
以下说明为什么CAP 原则三个要素最多只能同时实现两点,不可能三者兼顾。
假设有一个客户端C用户A,2台服务器,分别部署了2个同样的服务节点S1、S2,存放的数据都是V0,他们之间的网络可以互通,也就相当于分布式系统的两个部分。
操作流程
1、客户端A更新了数据V1到S1
2、S1节点这个消息告诉S2节点,想让S2页更新数据,却发生了网络故障,S2中保存的还是V0
3、客户端向S2请求数据,S2返回V0数据
分析
(1)系统网络发生了故障,但是系统依然可以访问,因此具有容错性。
(2)客户端A访问节点S1的时候更改了V0到V1,想要客户端A访问节点S2的时候是V1,因此需要等网络故障恢复,将S2节点的数据进行更新才可以。
(3)在网络故障恢复的这段时间内,想要系统满足可用性,是不可能的。因为可用性要求随时随地访问系统都是正确有效的。这就出现了矛盾。
正是这个矛盾所以CAP三个特性肯定不能同时满足。既然不能满足,那我们就进行取舍。
有二种选择:
第一,牺牲数据一致性,响应旧的数据V0给客户端;
第二,牺牲可用性,阻塞等待,直到网络连接恢复,数据更新操作完成之后,再给用户响应最新的数据V1。
取舍策略
CA without P:如果不要求P(不允许分区),则C(强一致性)和A(可用性)是可以保证的。但放弃P的同时也就意味着放弃了系统的扩展性,也就是分布式节点受限,没办法部署子节点,这是违背分布式系统设计的初衷的。
CP without A:如果不要求A(可用),相当于每个请求都需要在服务器之间保持强一致,而P(分区)会导致同步时间无限延长(也就是等待数据同步完才能正常访问服务),一旦发生网络故障或者消息丢失等情况,就要牺牲用户的体验,等待所有数据全部一致了之后再让用户访问系统。设计成CP的系统其实不少,最典型的就是分布式数据库,如Redis、HBase等。对于这些分布式数据库来说,数据的一致性是最基本的要求,因为如果连这个标准都达不到,那么直接采用关系型数据库就好,没必要再浪费资源来部署分布式数据库。
AP wihtout C:要高可用并允许分区,则需放弃一致性。一旦分区发生,节点之间可能会失去联系,为了高可用,每个节点只能用本地数据提供服务,而这样会导致全局数据的不一致性。典型的应用就如某米的抢购手机场景,可能前几秒你浏览商品的时候页面提示是有库存的,当你选择完商品准备下单的时候,系统提示你下单失败,商品已售完。这其实就是先在 A(可用性)方面保证系统可以正常的服务,然后在数据的一致性方面做了些牺牲,虽然多少会影响一些用户体验,但也不至于造成用户购物流程的严重阻塞。
一般来说,分区容错无法避免,因此可以认为 CAP 的 P 总是成立。CAP 定理告诉我们,剩下的 C 和 A 无法同时做到。