Advertisement

Google File System论文阅读难点笔记

阅读量:

阅读GFS论文时,发现有几个地方特别不容易理解,特记录如下。

一致性问题

在GFS系统中,文件被组织成块状结构,在每个存储单元都包含冗余副本的情况下进行管理,并将这些副本分散部署于不同的计算节点中。为了实现这一目标,请思考如何确保数据在各个副本之间的同步一致?

在论文中提到‘宽松的一致性模型’这一概念。通常认为‘宽松’是指并不严格要求一致性。那么其背后的原因是什么呢?这一做法的主要原因是为了简化系统的整体架构。

为什么会有一致性的问题?一致性问题产生的根源是什么?

写入操作失败,是导致不一致性的一个原因。

主要原因包括用户进行多路操作行为,在简化了系统设计的情况下缺乏复杂的同步机制。

一致性涉及到的重要概念:

  1. 一致性(consistency)通常用于描述系统中同一块数据在不同副本中的表现。
  2. 如果一次修改后,在保证一致性的同时确保所有客户端都能完整地看到这次修改,则该数据块被定义(defined)为明确可访问的状态(state)。

接下来看下表:

随机写 记录追加写
串行成功 定义的 定义但部分不一致
并发成功 一致但是未定义
失败 不一致
  • 随机写串行成功:由于执行过程达到了预期目标,在完成数据存储后文件偏移量与实际内容完美吻合;由于采用串行方式写作无并发冲突风险因此最终结果是最理想的状态即被正确地定义了。
  • 随机写并发成功:尽管没有同步机制可能导致多个独立的操作者同时对同一存储区域进行修改从而引发竞争性排斥;即使所有write操作均完成了但它们可能因被其他独立的操作干扰而被覆盖导致最终结果不确定甚至无法确定;然而GFS系统要求所有变更操作必须按照严格的顺序在不同节点上进行因此最终结果能够保持一致性即所有变更必须同步发生。
  • 追加写成功:无论采用串行方式还是并行方式从系统视角来看都是串行处理追加操作必须依次完成前一动作全部完成才能开始下一动作。“为什么会存在不一致的情况呢?”这是因为追加操作会影响文件尾部偏移量GFS系统会在数据全部提交前自动填充校准必要空间以确保后续追加数据能够正确衔接;但由于多个副本之间偏移量可能不一致导致部分区域出现无效数据这一现象的发生程度受到初始偏移量差异的影响。
  • 失败:当发生失败情况时不仅无法保证数据的一致性而且连明确状态也无法达到。

GFS是如何保证一致性的?它采取了两人上措施,一个是事前的,一个是事后的。事前的措施是变更无论是串行还是并发,都要先编号、排除,然后按相同的顺序应该到各个副本上,这样就保证了一致性。事后的措施是给每个副本定义版本号,随着变更的进行版本号依次变化,如果某个副本因为某种原因缺失了某次变更,那么它的版本号就会出现问题,并且GFS在周期性检测中能发现这种问题,此时这份副本就变成失效副本,不会再应用任何变更,GFS将些副本当垃圾回收并自动复制正确的副本实例补全。因为客户端会缓存副本位置信息,不能第一时间感知失效副本,也就是在失效的情况下有可能仍然对它进行读写。写的话没有问题,因为变更应用到了其它正确的副本,并且损失的副本会被GFS自动补全。如果失效副本被回收则写操作失败,并返回失败原因,则此时客户端可重新刷新副本位置缓存。读的话可能会有问题,但问题不太大。因为GFS大部分情况下都采用原子记录追加的方式,顺序的写顺序的读,一旦被写入,大部分情况下都不需要再去随机修改,因此这个时候客户端会读到提前结束的记录或者是块,或者是直接返回错误,此可客户端应该重新刷新副本位置缓存。

GFS的不一致性是客观存在的,客户端如何适应、应对这种情况呢?

首先尽量避免随机写特别是并发随机写,减少冲突发生的可能性。

选择适当的模式,在具体实施时可参考以下方法:首先按照顺序追加文件直至全部写满后进行整体读取处理;其次采用分步操作策略确保数据完整性;最后遵循"读写分离"原则将数据输入与内容解析分开以避免潜在的同步操作风险;同时尽量避免在同一操作过程中进行多线程处理从而保障数据完整性

实施周期性设置检查点以记录已处理的数据信息,并对尚未被进一步处理的数据块实施禁止操作以平衡读写速度

针对由于写入失败所导致的记录碎片,在记录中加入checksum字段;随后,在读取后进行检查以确认其有效性。

在设计阶段, 针对存在重复记录的情况, 为这些记录分配唯一的标识符; 通过该标识符来识别数据源并确定是否存在数据冗余

变更顺序与租赁机制问题

当多个客户端同时向同一个文件进行多路追加操作时(如果有多路客户端),而这些数据被复制存储到多个副本中(因为客户端同时追加)。为了确保整个系统的数据一致性(为了保证),GFS会为每个修改生成唯一的版本号,并将这些请求按时间排序(以便处理)。确保所有修改操作按时间顺序被应用到各个副本中(GFS首先会对所有的变更编号并排队),从而实现了各副本间的数据一致性(这也就意味着)。

从逻辑架构来看,GFS系统仅包含一个 master 节点,并且为了减轻其工作负担,在必要时引入了一种称为"租赁"的概念。这一机制的本质是将变更命令的接收、编号、排队及分发等职责转移至特定副本节点,并暂时将其权力与责任"租赁"出去以缓解 master 节点的工作压力。该角色的指定副本则被称为主副本节点(master node),由 master 节点从所有可用副本中选择并通知客户端相关操作信息;然而,在某些特定情况下(例如 master 节点可能取消主副本资格或使主副本失效/过期),该角色也可能被剥夺或失效;此时客户端需重新向 master 节点发起查询以获取最新信息。

STEP1:客户端告诉master,想对某个文件追加记录。

STEP2: master 生成所有副本的位置信息 , 第一个副本 即 master 选出的主副本节点 , 客户端将缓存这些位置信息 并随后进行相应的操作 。

STEP3:客户端将数据信息发送至副本节点。这里仅指简单的数据记录,并非实际存储于文件中。这些记录会被缓存池缓存,并未直接作用于文件本身。为了提高带宽利用率,在传输过程中会优先选择与自身位置较近的副本节点进行传输,并不遵循固定的顺序规则

STEP4:当客户端完成数据推送后提交变更请求以将STEP3中的缓存数据应用至文件中此时所发送的数据为控制信息包并必须发送给主副本节点可以看出在GFS架构中数据量与控制流是完全分离且相互独立的它们发生的时间点不同传播路径也各具特色

STEP5:该主副本节点可能会同时接收大量变更请求,在处理时会负责编号和排除,并将剩余请求分发至其他节点。无论是否为主副本或普通副本, 均按照此排序依次执行变更操作。

STEP6:普通节点告诉主副本节点变更完成。

STEP7:主副本节点告诉客户端变更完成。

上图中的明显箭头符号代表数据流动方向,在每个节点都实现了并行处理 upstream 和 downstream 数据流的状态下(即同时进行接收与发送操作),系统的带宽使用效率非常高

在步骤5中, 主副本节点收集所有变更, 并将它们安排好队列. 随后, 在各个节点上都会按照这一顺序来处理这些命令. 这意味着用户虽然同时发送了多个变更请求, 但在GFS内部依然会以串行的方式处理这些请求, 这明显导致了 writes 的速度下降.

关于记录追加的原子性

一种常见的做法是在大数据处理过程中进行数据更新或修改。该系统因此获得了重点支持。对于客户端而言?如果一个记录追加过程顺利完成,在后端系统管理下确保文件至少包含一条正确的记录。这意味着文件可能包含多条记录。其中一些可能出现碎片现象。这些细节并不会影响到普通用户的正常操作体验。

参考:http://www.importnew.com/3491.html 比较好的中文翻译

http://www.docin.com/p-842003858.html 英语原文

全部评论 (0)

还没有任何评论哟~