RM接收到客户端作业提交请求时会通过RPC server做回应,其实客户端就是通过ApplicationClientProtocol的RPC客户端提交作业的,客户端的提交流程参见Hadoop源码解析之YARN客户端作业提交流程,在提交阶段的代码中,客户端在获取新的JobId时,会调用到服务端getNewApplication来获得一个GetNewApplicationResponse,该返回类中包含了APP的ApplicationId,调度器资源信息。需要注意的是在RM的服务端有多个RPCserver,服务于作业提交的server为ClientRMService,默认监听18032端口,可以通过yarn.resourcemanager.address配置,下面是服务端的getNewApplication,包含在ClientRMService.java中。
//ClientRMService.java
public GetNewApplicationResponse getNewApplication(
GetNewApplicationRequest request) throws YarnException {
LOG.info("begin to getNewApplication");
//构建GetNewApplicationResponse对象
GetNewApplicationResponse response = recordFactory
.newRecordInstance(GetNewApplicationResponse.class);
//设置作业ID
response.setApplicationId(getNewApplicationId());
// Pick up min/max resource from scheduler...
// 设置调度器资源信息,作业ID设置完后,接下来设置调度器资源,目前包括CPU 内存两部分信息,相关函数有:
//yarn.scheduler.minimum-allocation-mb yarn.scheduler.minimum-allocation-vcores
//yarn.scheduler.maximum-allocation-mb yarn.scheduler.maximum-allocation-vcores,这些信息在调度器启动时指定。
response.setMaximumResourceCapability(scheduler
.getMaximumResourceCapability());
return response;
}
作业ID的获得通过getNewApplicationId,是由集群启动时间戳和计数器计算得来。
ApplicationId getNewApplicationId() {
LOG.info("begin to getNewApplicationId");
ApplicationId applicationId = org.apache.hadoop.yarn.server.utils.BuilderUtils
.newApplicationId(recordFactory, ResourceManager.getClusterTimeStamp(),
applicationCounter.incrementAndGet());
LOG.info("Allocated new applicationId: " + applicationId.getId());
return applicationId;
}
作业ID的构建函数:</