背景:
之前分析了flink的rpc,有了这个基础,可以了解flink的集群的主要工作机制,以及当中的设计思想,本次只看本地集群模式。
分析目标:
1、flink的集群启动脚本分析。
2、Flink Standalone 主节点 StandaloneSessionClusterEntrypoint 启动源码分析
ResourceManager 启动
DispatcherRunner启动
WebmonitorEndpoint启动
3、Flink Standalone 从节点 TaskManagerRunner 启动源码分析 TaskExecutor 启动(下篇分析)
4、TaskExecutor 和 ResourceManager 的注册,心跳和负载汇报(下篇分析)
一、启动脚本分析
如下图,启动脚本是从start-cluster.sh开始的。
该脚本会首先调用config.sh来获取master和worker,然后通过jobmanager.sh和taskmanager.sh分别启动jobmanager和taskmanager.
1、JobManager 的启动代码:standalonesession,实现类是:StandaloneSessionClusterEntrypoint
2、TaskManager 的启动代码:taskexecutor,实现类是:TaskManagerRunner
集群启动有支持3种 如下图所示:
这里先看StandaloneSessionClusterEntrypoint 类
为了避免图片过多,将进行简写
ClusterEntrypoint.runClusterEntrypoint(entrypoint){ ...... //启动集群 clusterEntrypoint.startCluster(){ runCluster(configuration, pluginManager){ synchronized (lock) { //初始化基础服务 initializeServices(configuration, pluginManager); //创建重要组件 createDispatcherResourceManagerComponentFactory.create(configuration); //创建dispatcher dispatcherResourceManagerComponentFactory.create(xxx);
....... } } } .....
初始化基础服务:
initializeServices(xxx){
synchronized (lock) {
//创建远程的rpc服务,主要基于akka进行的实现。
commonRpcService = RpcUtils.createRemoteRpcService(xxx);
//创建io线程。
ioExecutor = Executors.newFixedThreadPool(xxx);
//创建ha服务,
haServices = createHaServices(configuration, ioExecutor, rpcSystem);
//创建并启动文件服务
blobServer = new BlobServer(configuration, haServices.createBlobStore());
//创建心跳服务
heartbeatServices = createHeartbeatServices(configuration);
//创建一个graph存储服务
executionGraphInfoStore = createSerializableExecutionGraphStore
}
}
上面的基础服务后续深入分析。
这里先看创建重要组件
createDispatcherResourceManagerComponentFactory(xxxx){
DefaultDispatcherResourceManagerComponentFactory.createSessionComponentFactory(xxxxx){
new DefaultDispatcherResourceManagerComponentFactory( xxxx){
return new DefaultDispatcherResourceManagerComponentFactory(xxx)
}
}
}
上面的过程,如下图所示:
紧接看dispatcherResourceManagerComponentFactory.create(xxx);
dispatcherResourceManagerComponentFactory.create(xxx){
// TODO_MA 注释: Dispatcher 监听器
LeaderRetrievalService dispatcherLeaderRetrievalService = null;
// TODO_MA 注释: ResourceManager 监听器
LeaderRetrievalService resourceManagerRetrievalService = null;
// TODO_MA 注释: WebMonitorEndpoint
WebMonitorEndpoint> webMonitorEndpoint = null;
// TODO_MA 注释: ResourceManager
ResourceManagerService resourceManagerService = null;
// TODO_MA 注释: DispatcherRunner
DispatcherRunner dispatcherRunner = null;
try{
//没有就创建leaderRetriever
dispatcherLeaderRetrievalService = highAvailabilityServices.getDispatcherLeaderRetriever();
//
webMonitorEndpoint = restEndpointFactory.createRestEndpoint(xx);
webMonitorEndpoint.start();
//
resourceManagerService = ResourceManagerServiceImpl.create(resourceManagerFactory,xx);
dispatcherRunner = dispatcherRunnerFactory.createDispatcherRunner(xx);
//
resourceManagerService.start();
//包装了上面比较重要的三个组件webMonitorEndpoint、dispatcherRunner、resourceManagerService
return new DispatcherResourceManagerComponent(xxxx);
}catch(xxx){}
}
二、重要组件的启动WebMonitorEndpoint、ResourceManager、DispatcherRunner启动分析
2、1WebMonitorEndpoint启动分析
入口:DispatcherResourceManagerComponentFactory.create(....)
核心工作原理:
1. 初始化一大堆 Handler 和 一个 Router,并且进行排序去重,之后,再把每个 Handler 注册 到 Router 当中
2. 启动一个 Netty 的服务端
3. 启动内部服务:执行竞选!WebMonitorEndpoint 本身就是一个 LeaderContender 角色。如果竞选成功,则回调 isLeader() 方法
4. 竞选成功,其实就只是把 WebMontiroEndpoint 的 address 以及跟 zookeeper 的 sessionID 写入到 znode 中
5. 启动一个关于 ExecutionGraph 的 Cache 的定时清理任务
2.2ResourceManager 启动和初始化源码剖析
核心入口:DispatcherResourceManagerComponentFactory.create(....)
总结:
1、ResourceManager 是 RpcEndpoint 的子类,所以在构建 ResourceManager 对象完成之后,肯定会调用 start() 方法来启动这个 RpcEndpoint,然后就调准到它的 onStart() 方法执行。
2 、ResourceManager 是 LeaderContender 的子类,会通过 LeaderElectionService 参加竞选,如果竞选成功,则会回调 isLeader() 方法。
3、启动 ResourceManager 需要的一些服务:
两个心跳服务7 ResourceManager 和 TaskExecutor 之间的心跳、ResourceManager 和 JobMaster 之间的心跳
两个定时服务10 checkTaskManagerTimeoutsAndRedundancy() 检查 TaskExecutor 的超时
checkSlotRequestTimeouts() 检查 SlotRequest 超时
2.3 DispatcherRunner 启动和初始化源码剖析
核心入口:
DispatcherResourceManagerComponentFactory.create(....)
这里的dispatcherLeaderProcess是什么呢?
从这里可以看出来dispatcherLeaderProcess=SessionDispatcherxxxx
总结:
1、启动 JobGraphStore 服务
2、从 JobGraphStrore 恢复执行 Job, 要启动 Dispatcher
以上的几个重要组件都是启动jobmanager所启动的几个重要组件。