准备工作
首先会在SparkSubmit在main()方法中执行,然后根据提交的类型调用相应的方法,这里是”Submit”,调用submit()方法,submit()里面进行一些判断后,
使用反射Class.forName(childMainClass, true, loader),然后调用invoke()方法来调用程序员自己写的类,也就是自己写的程序
步骤
1.创建SparkEnv对象
main()方法里有调用SparkContext,SparkContext构造器使用createSparkEnv()方法,
这个方法使用SparkEnv.createDriverEnv(conf, isLocal, listenerBus)方法创建SparkEnv对象;
在SparkEnv类,调用create()方法来进行创建SparkEnv,返回的SparkEnv实例对象包含的对象
val envInstance = new SparkEnv(
executorId,
rpcEnv,
serializer,
closureSerializer,
serializerManager,
mapOutputTracker,
shuffleManager,
broadcastManager,
blockManager,
securityManager,
metricsSystem,
memoryManager,
outputCommitCoordinator,
conf)
rpcEnv
创建Netty分布式消息系统,是driver就启动,用的netty方式,用于接受Executor的汇报信息。
Serializer 和closureSerializer都是使用Class.forName反射生成的org.apache.spark.serializer.JavaSerializer类的实例。其中closureSerializer实例用来对Scala中的闭包进行序列化。
最后都是调用startServiceOnPort启动监听端口,只不过存在driver的这个节点在启动的时候多一个是用netty启动的,多了一个判断处理而已,但是这个节点仍然被认为是Executor。dirver的是netty的方式,而executor是采用akka的actor方式的。
serializerManager
val serializerManager = new SerializerManager(serializer, conf, ioEncryptionKey)
加密等操作
mapOutputTracker创建
作用; 用于跟踪map阶段任务的输出状态,此状态便于reduce阶段任务获取地址及中间输出结果。MapOutputTrackerMaster内部使用mapStatus:TimeStampedHashMap[Int,Array[MapStatus]]来维护跟踪各个map任务的输出状态。其中key对应shuffleId,Array存储各个map任务对应的状态信息MapStatus
根据是否为driver存在不同的创建方式:
-
如果当前应用程序为Driver,则创建MapOutputTrackerMaster,然后创建MapOutputTrackerMasterEndpoint,并且注册到RpcEndpoint系统中。
-
如果当前应用程序为Executor,则创建MapOutputTrackerWorker,并从RpcEndpoint持有MapOutputTrackerMasterEndpint的应用。
实例化shuffleManager
ShuffleManager负责管理本地及远程的block数据的shuffle操作。默认的SortShuffleManager通过持有的IndexShuffleBlockManger间接操作BlockManager中的DiskBlockManger将map结果写入本地,并根据shuffleId,mapId写入索引文件,也能通过MapOutputTrackerMaster中维护的mapStatuses从本地或者其他远程节点读取文件。
blockManager
val blockTransferService =
new NettyBlockTransferService(conf, securityManager, bindAddress, advertiseAddress,
blockManagerPort, numUsableCores)
val blockManagerMaster = new BlockManagerMaster(registerOrLookupEndpoint(
BlockManagerMaster.DRIVER_ENDPOINT_NAME,
new BlockManagerMasterEndpoint(rpcEnv, isLocal, conf, listenerBus)),
conf, isDriver)
// NB: blockManager is not valid until initialize() is called later.
val blockManager = new BlockManager(executorId, rpcEnv, blockManagerMaster,
serializerManager, conf, memoryManager, mapOutputTracker, shuffleManager,
blockTransferService, securityManager, numUsableCores)
块传输服务blockTransferService:
BlockTransferService默认为NettyBlockTransferService,使用Netty提供的异步事件驱动的网络应用框架,提供web服务及客户端,获取远程节点上Block的集合。
BlockManagerMaster介绍:
BlockManagerMaster负责对Block的管理和协调,具体操作依赖于BlockManagerMasterEndpoint。Driver和Executor处理的BlockManagerMaster的方式不同:
-
·如果当前应用程序为Driver,则创建BlockManagerMasterEndpoint,并且注册到RpcEndpoint中。
-
·如果当前应用程序为Executor, 则从RpcEndpoint中找到BlockManagerMasterEndpoint。
无论是Driver还是Executor,最后BlockManagerMaster的属性driverEndpoint将持有对BlockManagerMasterEndpoint的引用(RpcEndpointRef)。
创建块管理器BlockManager
:
BlockManager负责对Block的管理,只有在BlockManager的初始化方法initialize被调用后,它才是有效地。
创建广播管理器BroadcastManager
:
BroadcastManager用户将配置信息和序列化后的RDD、Job以及ShuffleDependency等信息在本地存储。如果为了容灾,也会复制到其他节点上。
BroadcastManager必须在其初始化方法initialize被调用后,才能生效。
创建监控系统MetricsSystem:
MetricsSystem.createMetricsSystem("driver", conf, securityManager)
MetricsSystem是Spark的监控系统。内部包含安全管理器
MemoryManager管理
val useLegacyMemoryManager = conf.getBoolean("spark.memory.useLegacyMode", false)
val memoryManager: MemoryManager =
if (useLegacyMemoryManager) {
new StaticMemoryManager(conf, numUsableCores)
} else {
UnifiedMemoryManager(conf, numUsableCores)
}
outputCommitCoordinator 输出协调者
val outputCommitCoordinator = mockOutputCommitCoordinator.getOrElse {
new OutputCommitCoordinator(conf, isDriver)
}
val outputCommitCoordinatorRef = registerOrLookupEndpoint("OutputCommitCoordinator",
new OutputCommitCoordinatorEndpoint(rpcEnv, outputCommitCoordinator))
outputCommitCoordinator.coordinatorRef = Some(outputCommitCoordinatorRef)