后知后觉仍然比不知不觉好一点,虽然我们努力最求的是先知先觉。
在阅读了Eric A. Brewer的keynote at the PODC和Gilbert and Lynch的Brewer's Conjecture and the Feasibility of Consistent,Available,Partition-Tolerant Web Service后,对CAP有了些初步的认识,也尝试弄清楚一些基本的问题。
1. 为什么我们需要知道CAP
记得当初学习数学科学(例如微分方程)的时候,如果求解一个问题,首先我们需要证明这个解的存在性。(没学过微分方程也可以回忆一下哥尼斯堡七桥问题)
现实生活中,我们往往面临的是非常具体(甚至琐碎)的问题,我们也在不断付出巨大的努力的尝试解决它们。如果问题棘手,发现一时无法走出的困境后,往往会寻求新的设计方案来解决问题。每一个方案(系统)设计之初,参与设计者往往对未来这个方案充满了憧憬,事实上,新方案也一般能解决现有系统的瓶颈。但是新方案运行一段时间后,我们又会重新发现,我们绕过了一些问题,面对的是一些新的困境。
为了避免这种情况,在设计新方案的时候,我们需要尝试弄清楚我们现在系统解决了哪些问题,没有解决哪些问题,无法解决哪些问题;设计新系统,我们能够解决哪些,无法解决哪些。
CAP理论(也许不能说是严格理论,因为我们往往在C、A、P之前寻求平衡)便是基于这样的思考,产生的理论。
2. 什么是CAP
即使是现在,我仍然不是很理解CAP,所以本文也无法清楚的阐述"什么是CAP",这里将列出我的认识,和看到并觉得靠谱的认识。
CAP是Eric A. Brewer在PODC上首次提出,Brewer的一部分工作便设计大型的分布式系统设计与实现,例如Global Search Engines、Distributed Web Caches等。所以CAP理论也是基于分布式(Distributed Systems)的系统,所以下面全部的内容,都需要放到分布式系统的中去理解,否则你会迷失。
Consistency是容易理解的;关于Availability和Partition tolerance,Jeff Darcy在文章Availability and Partition Tolerance做了如下阐述CAP是指Consistency, availability and partition tolerance的缩写,不过理解这三个概念并不容易。CAP理论指出,这三者不可兼得。
“Availability is sacrificed if certain nodes are forced to wait for unbounded time because of a failure. This includes the common approach of forcing non-quorum nodes down, which Brewer alludes to.”
“Partition tolerance is sacrificed if certain requests are forced to wait for unbounded time because of a failure. This is most often the case when a node holding a lock cannot be reached, and quorum loss is not used to break the lock.”
虽然看起来很晦涩,不过这已经是能够看到最清晰的解释了。(如果你仔细看这篇文章后面的评论,还有发现很多有意思的东西)
3. Sample of CAP
符合CAP设计哲学中,两个最典型的案例便是:Google的BigTable和Amazon的Dynamo。前者是一个CA系统,后者则是一个AP系统。
4. CAP 和 MySQL
这里以MySQL Replication(Master-Slave)方案为例。在MS结构中,节点M和节点S,都可以对外提供服务,当其中的一个节点故障,另一个节点仍然能够对外提供服务,所以MS方案认为是满足Availability的;目前MS结构仍然是异步的方式运行,即当主库写入时,备库未必一定也写入了,备库甚至允许短暂和主库断开连接,而且当主库处理请求时,也无需确认备库的状态,所以MS结构是满足Partition tolerance的;但是由于MS结构的异步特性,我们看到主备的数据是可能不一致的,即不满足Consistency。
Semi-sync Replication则是在Consistency要求更严格,同时在部分失去Partition tolerance;如果MySQL使用DRBD(严格模式) 做HA方案,则实现了Consistency,就失去了Partition tolerance。