SparkContext是程序与Spark集群连接的枢纽。它主要做了以下3件事。
- 创建并初始化TaskScheduler。
- 创建并初始化DAGScheduler
- 创建并初始化Spark UI
下面分别介绍他们的具体流程。
创建并初始化TaskScheduler
- 在创建SparkContext的时候会调用createTaskScheduler()的方法进而创建一个TaskSchedulerImpl的对象。这也就是我们常说的TaskScheduler对象。
- 而TaskSchedulerImpl的底层是基于SparkDeploySchedulerBackend(Spark展示调度后端)的。SparkDeploySchedulerBackend会接受TaskSchedulerImpl的控制,它实际上负责TaskScheduler注册Application到Master,同时也会负责Worker中的Executor反注册在TaskScheduler。
- 接下来执行TaskSchedulerImpl的init方法创建一个调度池,而且这个调度池会有自己的调度算法比如说常见的先进先出。
- 接下来就要启动任务调度了。调用TaskSchedulerImpl.start(),然后再调用
SparkDeploySchedulerBackend.start()进而构建出AppClient对象,AppClient会启动ClientActor线程,这个线程将要调用registerWithMaster()与tryRegisterAllMaster()向Master发送一个RegisterApplication(里面分装了这一个case class ,这个class封装了Application的众多信息)代表这个我们的Application向Master注册的过程。
- 紧接着Master会将任务分配到各个Woker上,Woker也会开启Executor并且向TaskScheduler反向注册。
- 到此,SparkContext的TaskScheduler初始化完毕然后将会正式执行Spark的计算过程直到结束。
它的初始化流程如下图所示:
创建并初始化DAGScheduler
DAGScheduler是一个基于stage调度机制的调度层,他会基于每一个job计算一个关于stage的DAG图(计算流程有向无环图)。同时追踪RDD的stage是否被物化(物化是指:是否被写到内存或者是硬盘上),并且找到一条最优的路径调度和运行job。具体来说就是将job的stage作为taskset提交到TaskSchedulerImpl上。
除了生成stage的DAG之外它还负责每个task的运行最佳位置。此外他还会处理由shuffle输出文件丢失导致的失败,在这种情况下stage会被重新提交。但是如果stage的失败不是由shuffle丢失数据而造成的也就是说它是一种内部的失败,这时就会被TaskScheduler处理,他会重新实验每个task,知道最后是在不行才会重新提交这个stage。
这里有一个比较重要的类DAGSchedulerEventProcessActor,DAGScheduler底层是基于这个类来通信的。
创建并初始化Spark UI
Spark UI就是一个Spark运行任务监控的web界面,它的底层是一个基于jetty的web程序来提供服务。(在Master的4040端口上)。
最后,感谢石杉老师!