Spark的RDD如何实现容错?

13

Spark 的核心概念是弹性分布式数据集(RDD),它是一个容错的元素集合,可以并行操作。但是,我没有找到 RDD 完成容错的内部机制。能否有人描述一下这个机制?谢谢。

1个回答

28

让我用我理解的非常简单的术语来解释。

当处理数据的节点之一崩溃时,集群中可能会发生故障。在Spark术语中,RDD被分割成分区,每个节点(称为executors)在任何时间点都在对一个分区进行操作。(理论上,每个执行器可以根据作业分配的核心数与RDD中存在的分区数决定是否分配多个任务)。

通过操作,实际上是一系列Scala函数(根据函数是纯函数还是有副作用的,在Spark术语中称为变换和操作)在RDD的一个分区上执行。这些操作组合在一起,并且Spark执行引擎将它们视为操作的有向无环图。

现在,如果在依赖于操作Y的操作Z的中间,某个特定节点崩溃,而操作Y又依赖于操作X。集群管理器(YARN/Mesos)发现该节点已死,并尝试分配另一个节点来继续处理。将告诉这个新节点对RDD的特定分区以及它必须执行的一系列操作X->Y->Z(称为lineage),并传递从应用程序代码创建的Scala闭包。现在,新节点可以愉快地继续处理,而且实际上没有数据丢失。

Spark还使用这种机制来保证仅执行一次处理,但做任何有副作用的操作(例如在Spark Action块中调用数据库)可能会被调用多次。但是,如果将转换视为从一个RDD到另一个RDD的纯函数映射,则可以放心地确保结果RDD仅对源RDD进行一次处理。

Spark中容错领域非常广泛,需要更大的解释。我希望看到其他人提出有关如何实现等技术细节的问题。感谢这个伟大的主题。


同意集群管理器会处理失败。但每个分区一个执行器是否正确?也就是说,如果我有2000个分区,那么我将拥有2000个执行器用于并行处理?这总是成立的吗? - Abhijit
1
一个执行器一次只能处理一个分区,当它完成时,该执行器将处于空闲状态。如果仍有未执行的分区,则驱动程序将任务调度到此空闲执行器。这意味着一个执行器可以处理多个分区。 - Tom
为了准确起见,重新安排失败的任务到另一个执行器上并非Yarn的责任,而是驱动程序的责任。 - Tom
Yarn的职责是在容器中重新启动执行器,而驱动程序的职责是重新启动该执行器上失败的任务。 - Geek

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接