Two-Phase-Commit for Distributed In-Memory Caches--reference
Part I
reference from:http://gridgain.blogspot.kr/2014/09/two-phase-commit-for-distributed-in.html
2-Phase-Commit is probably one of the oldest consensus protocols and is known for its deficiencies when it comes to handling failures, as it may indefinitely block the servers waiting in prepare state. To mitigate this, a 3-Phase-Commit protocol was introduced which adds better fault tolerance at the expense of extra network round-trip message and higher latencies.
I would like to extend these traditional quorum concepts into distributed in-memory caching, as it is particularly relevant to what we do at GridGain. GridGain too has 2-phase-commit transactions, but unlike disk-based persistent systems, GridGain does not need to add a 3rd phase to the commit protocol in order to preserve data consistency during failures.
We want to avoid the 3-Phase-Commit protocol because it adds an additional network round-trip and has a negative impact on latencies and performance.
In GridGain, the data is partitioned in memory, which in the purest form means that every key-value pair is assigned to a specific node within the cluster. If for example, we have 100 keys and 4 nodes, then every node will cache 100 / 4 = 25keys. This way the more nodes we have, the more data we can cache. Of course, in real life scenarios, we also have to worry about failures and redundancy, so for every key-value pair we will have 1 primary copy, and 1 or more backup copies.
Let us now look at the 2-Phase-Commit protocol in more detail to see why we can avoid the 3rd commit phase in GridGain.
Two-Phase-Commit Protocol
Generally the 2-Phase-Commit protocol is initiated whenever an application has already made a decision to commit the transaction. The Coordinator node sends a Prepare message to all the participating nodes holding primary copies (primary nodes), and the primary nodes, after acquiring the necessary locks, synchronously send the "Prepare"message to the nodes holding backup copies (backup nodes). Once every node votes "Yes", then the"Commit" message is sent and the transaction gets committed.

Advantages of In-Memory
So, why does in-memory-only processing allow us to avoid the 3rd phase as opposed to persistent disk-based transactions? The main reason is that the in-memory cache is purely volatile and does not need to worry about leaving any state behind in case of a crash. Contrast that to the persistent architectures, where we need to worry whether the state on disk was committed or not after a failure had occurred.
Another advantage of in-memory-only distributed cache is that the only valid vote for the "Prepare" message is "Yes". There is really no valid reason for any cluster member to vote "No". This essentially means that the only reason a rollback should happen is if the Coordinator node crashed before it was able to send the "Prepare" message to all the participating nodes.
Now, that we have the ground rules settled, let's analyze what happens in case of failures:
Backup Node Failures
If a backup node fails during either "Prepare" phase or "Commit" phase, then no special handling is needed. The data will still be committed on the nodes that are alive. GridGain will then, in the background, designate a new backup node and the data will be copied there outside of the transaction scope.
Primary Node Failures
If a primary node fails before or during the "Prepare" phase, then the coordinator will designate one of the backup nodes to become primary and retry the "Prepare" phase. If the failure happens before or during the "Commit" phase, then the backup nodes will detect the crash and send a message to the Coordinator node to find out whether to commit or rollback. The transaction still completes and the data within distributed cache remains consistent.
Coordinator Node Failures
Failure of the Coordinator node becomes a little tricky. Without the Coordinator node, neither primary nodes, nor backup nodes know whether to commit the transaction or to rollback. In this case the "Recovery Protocol" initiates, and all the nodes participating in the transaction send a message to every other participating node asking whether the"Prepare" message was received. If at least one of the nodes replied "No", then the transaction will be rolled back, otherwise the transaction will be committed.
Note that after all the nodes received the "Prepare" message, we can safely commit, since voting "No" is impossible during the "Prepare" phase as stated above.
It is possible that some nodes will have already committed the transaction by the time they have received the Recovery Protocol message from other nodes. For such cases, every node keeps a backlog of completed transaction IDs for a certain period of time. If there is no ongoing transaction with given ID found, then the backlog is checked. If the transaction was not found in the backlog, then it was never started, which means that the failure had occurred before the Prepare phase was completed and it is safe to rollback.
Since the data is volatile, and does not leave any state after the crash, it does not really matter if any of the primary or backup nodes also crashed together with the coordinator node. The Recovery Protocol still works the same.

Conclusion
Note that we are able to fully recover the transaction without introducing the 3rd commit phase mainly because the data in distributed in-memory caches is volatile and node crashes do not leave any state behind.
The important advantage of the 2-Phase-Commit Recovery Protocol in GridGain over the 3-Phase-Commit is that, in the absence of failures, the recovery protocol does not introduce any additional overhead, while the 3-phase-commit adds an additional synchronous network roundtrip to the transaction and, therefore, has negative impact on performance and latencies.
GridGain also supports modes where it works with various persistent stores including transactional databases. In my next blog, I will cover the scenario where a cache sits on top of a transactional persistent store, and how the 2-Phase-Commit protocol works in that case.
Part II
reference from:http://java.dzone.com/articles/two-phase-commit-memory-caches
Generally, persistent disk-oriented systems will require the additional 3rd phase in commit protocol in order to ensure data consistency in case of failures. In my previous blog I covered why the 2-Phase-Commit protocol (without 3rd phase) is sufficient to handle failures for distributed in-memory caches. The explanation was based on the open source GridGain architecture, however it can be applied to any in-memory distributed system.
In this blog we will cover a case when an in-memory cache serves as a layer on top of a persistent database. In this case the database serves as a primary system of records, and distributed in-memory cache is added for performance and scalability reasons to accelerate reads and (sometimes) writes to the data. Cache must be kept consistent with database which means that a cache transaction must merge with the database transaction.
When we add a persistent store to an in-memory cache, our primary goal is to make sure that the cache will remain consistent with on-disk database at all times.
In order to keep the data consistent between memory and database, data is automatically loaded on demand whenever a read happens and the data cannot be found in cache. This behavior is called read-through. Alternatively, whenever a write operation happens, data is stored in cache and is automatically persisted to the database. This behavior is called write-through. Additionally, there is also a mode called write-behind which batches up the writes in memory and flushes them to the database in one bulk operation (we will not be covering this mode here).



Conclusion
Two-Phase-Commit for Distributed In-Memory Caches--reference的更多相关文章
- XA transaction ,JTA , two phase commit , GTX0-j
本文主要是对以前一直迷惑的几个名字的学习. xa transaction 简单查了一下,大概就是 distributed transaction. 相比传统的transaction而言,传统的tra ...
- Satisfying memory ordering requirements between partial reads and non-snoop accesses
A method and apparatus for preserving memory ordering in a cache coherent link based interconnect in ...
- Why Memory Barrier?
引言:xchg做了什么? 首先,xchg eax, ecx并不会比mov edx, eax + mov eax, ecx + mov ecx, edx这三条指令加一起快,原因是xchg有副作用. Mi ...
- Apache Spark 2.2.0 中文文档 - Spark RDD(Resilient Distributed Datasets)论文 | ApacheCN
Spark RDD(Resilient Distributed Datasets)论文 概要 1: 介绍 2: Resilient Distributed Datasets(RDDs) 2.1 RDD ...
- Apache Spark RDD(Resilient Distributed Datasets)论文
Spark RDD(Resilient Distributed Datasets)论文 概要 1: 介绍 2: Resilient Distributed Datasets(RDDs) 2.1 RDD ...
- Spark的核心RDD(Resilient Distributed Datasets弹性分布式数据集)
Spark的核心RDD (Resilient Distributed Datasets弹性分布式数据集) 原文链接:http://www.cnblogs.com/yjd_hycf_space/p/7 ...
- [原]git的使用(一)---建立本地仓库、add和commit、status和git diff、版本回退使用git reset
在window下已经安装了git的环境 1.建立本地仓库 mkdir test #建立test目录 cd test #进入目录 git init # ...
- spark hadoop 对比 Resilient Distributed Datasets
hadoop 迭代消耗大 每次迭代启动一个完整的MapReduce作业 spark 首要目标就是避免运算时 过多的网络和磁盘IO开销 Resilient Distributed Datasets ht ...
- Distributed Symmetric Multiprocessing Computing Architecture
Example embodiments of the present invention includes systems and methods for implementing a scalabl ...
- Method and apparatus for training a memory signal via an error signal of a memory
Described herein is a method and an apparatus for training a memory signal via an error signal of a ...
随机推荐
- c#读取通达信历史数据的方法
public Bar ReadBarMin(BinaryReader br, int instrumentId, long size) { int date = br.ReadUInt16(); in ...
- JavaScript_数组
/** * 数组本身也是对象 * js中数组类似于java里的map容器 长度可随意改变 ,元素类型任意 * */ // var arr = new Array(); // var arr = [1, ...
- cocos2d-x 读取 json 文件并用 jsoncpp 做解析
一码胜万言(请看注释) CclUtil.h // // CclUtil.h // PracticeDemo // // Created by kodeyang on 8/1/13. // // #if ...
- Java学习----对象的构造
public class Teacher { private String teacherName; private String gendar; // 构造方法:初始化属性值,没有返回类型 publ ...
- bootstrap sr-only
有时候 UI 上会出现一些仅供视觉识别的元素,比如说“汉堡包菜单按钮”,只有视力正常的人才能清楚辨识这些元素的作用.而残障人士,比如弱势或盲人是不可能知道这些视觉识别元素是什么的.他们上网使用的是屏幕 ...
- angularJS中如何写控制器
angularJS中的控制器是一个函数,用来向视图作用域中添加额外的功能,我们用它来给作用域对象设置初始状态,并添加自定义行为 当我们在页面上创建一个新的控制器时,angularJS会生成并传递一个新 ...
- 折半插入排序(Binary Insertion Sort)的C语言实现
原创文章,转载请注明来自钢铁侠Mac博客http://www.cnblogs.com/gangtiexia 折半插入排序(Binary Insertion Sort)的基本思想是将新记录插入到已经 ...
- WinPcap编程(三)
1.过滤器设置 设置过滤器,得到你想要的哪种类型的包.Like WireShark. 过程:编译过滤器,然后设置过滤器.直接上参考文档的代码: if (d->addresses != NULL) ...
- Heapsort 堆排序算法详解(Java实现)
Heapsort (堆排序)是最经典的排序算法之一,在google或者百度中搜一下可以搜到很多非常详细的解析.同样好的排序算法还有quicksort(快速排序)和merge sort(归并排序),选择 ...
- GIve Me A Welcome Hug!
类似于初来乍到,和大家打个招呼,并矫情的希望路人也能回赠我一个welcome hug. 到了这种园子那一定是做CS相关的了,一直以为如果能够坚持写技术博客,那一定会对自己的内力有十足的提升.借用一位前 ...