阅读目录
1、checkpoint的使用
2、checkpoint的内容
3、checkpoint的写过程
4、Streaming checkpoint
5、checkpoint的读过程
一、checkpoint的使用
checkpoint的使用很简单
1、对于普通应用,首先要设置checkpoint目录,使用SparkContext的setCheckpointDir设置,然后对具体的RDD数据集调用checkpoint方法即可。
2、对流处理应用(结构化流),写出流时必须设置checkpoint,否则会报错,未设置checkpoint目录异常。用.option(“checkpointLocation”, “your checkpoint-pathname”)设置即可。
二、checkpoint的内容
下面这个类包含了和checkpoint相关的所有信息,类的每一个实例对应着一个RDD。管理着实施检查点的过程,也通过提供更新的分区、迭代器以及首选位置来管理检查点后的RDD的状态。
private[spark] abstract class RDDCheckpointData[T: ClassTag](@transient private val rdd: RDD[T])
extends Serializable {
// The checkpoint state of the associated RDD.
protected var cpState = Initialized
// The RDD that contains our checkpointed data
private var cpRDD: Option[CheckpointRDD[T]] = None
通过这个类我们可以看到,这个类记录了RDD是否被checkpoint,以及持久化的RDD内容。
具体写入的内容:
1、RDD内容。
2、RDD的分区器,Partitioner。
三、checkpoint的写过程(对应reliable)
RDD.doCheckpoint()-->
RDDCheckpointData.checkpoint()-->
RDDCheckpointData.doCheckpoint()-->
ReliableRDDCheckpointData.doCheckpoint()-->
ReliableCheckpointRDD.writeRDDToCheckpointDirectory(rdd, cpDir)-->
sc.runJob(originalRDD, writePartitionToCheckpointFile[T](checkpointDirPath.toString, broadcastedConf) _)-->
ReliableCheckpointRDD.writePartitionToCheckpointFile
1、Checkpoint的过程也就是保存RDD的过程,RDD.doCheckpoint()在使用该RDD的任务完成之后调用(所以,RDD已经被物化并存储在内存中),并且这一函数在RDD的所有的祖先RDD上递归调用。
abstract class RDD[T: ClassTag](
@transient private var _sc: SparkContext,
@transient private var deps: Seq[Dependency[_]]
) extends Serializable with Logging {
/**
* checkpoint过程也就是保存RDD的过程,这一函数在使用该RDD的任务完成之后调用(所以,RDD已经被物化并存储
* 在内存中),并且这一函数在RDD的所有的祖先RDD上递归调用。
*/
private[spark] def doCheckpoint(): Unit = {
RDDOperationScope.withScope(sc, "checkpoint", allowNesting = false, ignoreParent = true) {
if (!doCheckpointCalled) {
doCheckpointCalled = true
if (checkpointData.isDefined) {
if (checkpointAllMarkedAncestors) {
// TODO We can collect all the RDDs that needs to be checkpointed, and then checkpoint
// them in parallel.
// 先Checkpoint父RDD,因为在checkpoint了自身RDD之后,自身RDD的沿袭图将被截断
dependencies.foreach(_.rdd.doCheckpoint())
}
checkpointData.get.checkpoint()
} else {
dependencies.foreach(_.rdd.doCheckpoint())
}
}
}
}
2、在对RDD设置检查点之后,在RDD上首次调用action操作并完成后立即调用该方法,持久化该RDD的内容,checkpoint内部调用了doCheckpoint执行具体行为。
private[spark] abstract class RDDCheckpointData[T: ClassTag](@transient private val rdd: RDD[T])
extends Serializable {
final def checkpoint(): Unit = {
// Guard against multiple threads checkpointing the same RDD by
// atomically flipping the state of this RDDCheckpointData
RDDCheckpointData.synchronized {
if (cpState == Initialized) {
cpState = CheckpointingInProgress