原型系统——动态调整提交时间戳减少事务中止率
MaaT: Effective and scalable coordination of distributedtransactions in the cloud VLDB 2014
这篇论文可以称为是为OCC摇旗呐喊的战斗檄文。论文首先提出了事务级云存储系统的概念,有代表性的系统如工业界的Spanner、 学术界的Calvin、开源界的MySQL Cluster。与传统事务级云数据库的区别在于更加透明的数据分区,包括自动化的分区拆分、合并、迁移、负载均衡, 这使得高效的跨结点分布式事务成为一个必选功能。
当前实现跨结点分布式事务的并发控制技术要么是2PL(Spanner、MySQL Cluster),要么是静态锁(Calvin,对事务操作进行静态分析后提前加锁),而OCC仅在应用层或Megastore中有所应用。OCC没有被普遍使用的原因有如下两点:
• 就适用场景来看,OCC适合于交互式或系统内部组件同步延时较大的场景,而在数据库系统内,磁盘、网络延时通常以毫秒计,OCC导致事务中止浪费计算资源的开销劣势远大于减少同步开销的优势
• 在分布式数据库实现中,OCC在写入阶段的原子提交协议依然依赖于2PC中的锁机制,没有彻底消除锁机制在云环境中可能会造成的死锁、降低事务吞吐量、系统资源利用率下降等问题
但是在云环境下,一个理想的云数据库应该满足如下要求:
• 在长事务、跨结点事务、高数据热点、高通信延时等场景下依然能够支持高事务吞吐率
• 高效的CPU利用率
• 高扩展性,减少系统内的同步点
• 高并发场景下没有系统性能抖动
• 系统无死锁或永久阻塞点
OCC在这种场景下是有技术优势的,因此,论文致力于实现一个消除2PC中的锁机制且大幅降低事务误中止率的分布式数据库系统MaaT。MaaT的理论基础基于论文[8]并在系统实现上进行了优化,其基本思想如下:
concurrent7
基本数据结构:
• 在事务访问的每个结点上需要维护内存事务表,记录事务的提交时间戳区间及当前状态- (runing/validated/committed/aborted)
• 每个数据对象维护一个最大读时间戳和最大写时间戳,这些时间戳均为已提交事务的提交时间戳
• 每个数据对象维护读/写过该对象的活跃事务号
基本流程:
1.读取阶段
① 在事务请求结点上分配一个全局唯一事务号,并在内存事务表中初始化事务信息(提交时间戳区间设置为0到正无穷,状态设置为running)
② 事务执行过程中第一次访问任意远程结点上的数据时都需要在结点本地的内存事务表中建立事务相关初始信息
③ 根据读写类型区别操作
读操作
– 将事务号加入读对象的未提交读事务号列表
– 返回读对象数据、读对象上当前加写锁的活跃事务号及读对象的最大写时间戳(事务提交时需保证提交时间戳小于所有该对象上写事务的时间戳并大于最大写时间戳)
– 客户端将返回数据缓存在事务私有内存中
写操作
将更新数据写入客户端的事务私有内存中
2.验证阶段
① 客户端发送预写/验证消息到所有相关数据服务器(读写涉及到的服务器),消息中包括与服务器相关的读集、写集及在读取阶段从服务器获取的信息(所有在读对象上加写锁的活跃事务号及最大写时间戳)
② 预写(处理服务器上的写操作)
收到消息的服务器将事务号加入写对象的未提交写事务列表
写事务日志
获取在写对象上加读锁的活跃事务号及最大读提交时间戳(事务提交时需保证提交时间戳大于所有该对象上读事务的时间戳并大于最大读时间戳)
获取在写对象上加写锁的活跃事务号
③ 验证(保证事务的串行化顺序按提交时间戳排序,通过调整事务提交时间戳区间的上下限实现,调整的原则为尽量减少事务中止率)
对于读集中的对象,需要保证验证事务能在读对象的最大写时间戳之后提交
对于读对象上的加写锁事务,需要保证在验证事务之后提交
对于写集中的对象,需要保证验证事务在写对象的最大读时间戳之后提交
对于写对象上的加读锁事务,需要保证在验证事务之前提交
对于写对象上的加写锁事务,需要保证在验证事务之后提交
④ 验证结束后,如果验证事务的提交时间戳区间有效(下限小于等于上限),则将事务状态改为validated;否则,将事务状态改为aborted
⑤ 各结点通知客户端事务状态及调整后的提交时间戳区间
3.写入阶段
① 如果有结点返回aborted,则事务最终状态为aborted
② 如果所有结点均返回committed,则计算所有提交时间戳区间的交集,区间无效,则事务最终状态为aborted;否则事务最终状态为committed,此时客户端需要从有效区间中选取任意的时间戳作为该事务的提交时间戳
③ 客户端向相关数据结点发送事务提交或中止消息,提交消息中包含更新数据及确定的提交时间戳
④ 对于abort消息,数据结点将本地事务表中的事务状态改为aborted,删除该事务在数据对象上加过的锁并记录事务中止日志
⑤ 对于committed消息,数据结点将本地事务表中的事务状态改为committed,提交时间戳区间设置为客户端确定的时间戳,删除该事务在数据对象上加过的锁并记录事务提交日志
⑥ 对于读集中的数据对象,如果事务提交时间戳大于读对象的最大读时间戳,则将读对象的最大读时间戳设置为事务提交时间戳
⑦ 对于写集中的数据对象,如果事务提交时间戳大于写对象的最大写时间戳,则将写对象的最大写时间戳设置为事务提交时间戳并修改写对象的内容
论文提出的OCC实现方案被2017年的VLDB论文[21]作为测试OCC性能的参考实现,间接证明这里提出的OCC算法已经得到了学术界的认可,虽然论文[21]中对新OCC算法的性能与其它并发控制算法的比较仍然没有正面评价,但性能瓶颈已经转移到网络传输及CPU计算消耗,事务中止率及同步开销已成为性能瓶颈的次要因素,OCC的扩展性得到了提高。
以上为分布式技术专题之并发系列三:乐观并发控制之原型系统(动态调整提交时间戳减少事务中止率),「分布式技术专题」是国产数据库hubble团队精心整编,专题会持续更新,欢迎大家保持关注。