yarn资源调度器

yarn资源调度器

一、yarn的概述

定义:yarn是一个资源调度平台,负责为运算程序提供其运算资源,相当于一个分布式的操作系统平台,而MapReduce等运算程序则相当于运算于操作系统之上的运用程序

二、yarn架构

从YARN的架构来看,它由ResourceManager、NodeManager、JobHistoryServer、Containers、Application Master、job、Task、Client组成。

组件的主要功能介绍:

(1)ResourceManager:

  • 处理客户端请求

  • 启动/监控ApplicationMaster

  • 监控NodeManager

  • 资源分配与调度

(2)ApplicationMaster:

  • 为应用程序申请资源,并分配给内部任务

  • 任务调度、监控与容错

(3)NodeManager:

  • 单个节点上的资源管理

  • 处理来自ResourceManger的命令

  • 处理来自ApplicationMaster的命令

(4)Container:

  • 对资源抽象和封装,目的是为了让每个应用程序对应的任务完成执行

(5)JobHistoryServer:

  • 负责查询job运行进度及元数据管理。

(6)job:

  • 是需要执行的一个工作单元:它包括输入数据、MapReduce程序和配置信息。job也可以叫作Application。

(7)task:

  • 一个具体做Mapper或Reducer的独立的工作单元。task运行在NodeManager的Container中。

(8)Client:

  • 一个提交给ResourceManager的一个Application程序。

(1)ResourceManager

​ ResourceManager(RM)是一个全局的资源管理器,负责整个系统的资源管理和分配,主要包括两个组件,即调度器(Scheduler)和应用程序管理器(Applications Manager)。 ​ 调度器接收来自ApplicationMaster的应用程序资源请求,把集群中的资源以“容器”的形式分配给提出申请的应用程序,容器的选择通常会考虑应用程序所要处理的数据的位置,进行就近选择,从而实现“计算向数据靠拢”。 ​ 容器(Container)作为动态资源分配单位,每个容器中都封装了一定数量的CPU、内存、磁盘等资源,从而限定每个应用程序可以使用的资源量。 调度器被设计成是一个可插拔的组件,YARN不仅自身提供了许多种直接可用的调度器,也允许用户根据自己的需求重新设计调度器。 ​ 应用程序管理器(Applications Manager)负责系统中所有应用程序的管理工作,主要包括应用程序提交、与调度器协商资源以启动ApplicationMaster、监控ApplicationMaster运行状态并在失败时重新启动等。

(2)ApplicationMaster

ResourceManager接收用户提交的作业,按照作业的上下文信息以及从NodeManager收集来的容器状态信息,启动调度过程,为用户作业启动一个ApplicationMaster。

ApplicationMaster的主要功能是:

(1)当用户作业提交时,ApplicationMaster与ResourceManager协商获取资源,ResourceManager会以容器的形式为ApplicationMaster分配资源;

(2)把获得的资源进一步分配给内部的各个任务(Map任务或Reduce任务),实现资源的“二次分配”;

(3)与NodeManager保持交互通信进行应用程序的启动、运行、监控和停止,监控申请到的资源的使用情况,对所有任务的执行进度和状态进行监控,并在任务发生失败时执行失败恢复(即重新申请资源重启任务);

(4)定时向ResourceManager发送“心跳”消息,报告资源的使用情况和应用的进度信息;

(5)当作业完成时,ApplicationMaster向ResourceManager注销容器,执行周期完成。

(3)NodeManager

NodeManager是驻留在一个YARN集群中的每个节点上的代理,主要负责:

  • 容器生命周期管理。

  • 监控每个容器的资源(CPU、内存等)使用情况。

  • 跟踪节点健康状况。

  • 以“心跳”的方式与ResourceManager保持通信。

  • 向ResourceManager汇报作业的资源使用情况和每个容器的运行状态。

  • 接收来自ApplicationMaster的启动/停止容器的各种请求 。

需要说明的是,NodeManager主要负责管理抽象的容器,只处理与容器相关的事情,而不具体负责每个任务(Map任务或Reduce任务)自身状态的管理,因为这些管理工作是由ApplicationMaster完成的,ApplicationMaster会通过不断与NodeManager通信来掌握各个任务的执行状态。

三、yarn提交作业全过程

(1)作业提交

第1步:Client调用job.waitForCompletion方法,向整个集群提交MapReduce作业。

第2步:Client向RM申请一个作业id。

第3步:RM给Client返回该job资源的提交路径和作业id。

第4步:Client提交jar包、切片信息和配置文件到指定的资源提交路径。

第5步:Client提交完资源后,向RM申请运行MrAppMaster。

(2)作业初始化

第6步:当RM收到Client的请求后,将该job添加到容量调度器中。

第7步:某一个空闲的NM领取到该Job。

第8步:该NM创建Container,并产生MRAppmaster。

第9步:下载Client提交的资源到本地。

(3)任务分配

第10步:MrAppMaster向RM申请运行多个MapTask任务资源。

第11步:RM将运行MapTask任务分配给另外两个NodeManager,另两个NodeManager分别领取任务并创建容器。

(4)任务运行

第12步:MR向两个接收到任务的NodeManager发送程序启动脚本,这两个NodeManager分别启动MapTask,MapTask对数据分区排序。

第13步:MrAppMaster等待所有MapTask运行完毕后,向RM申请容器,运行ReduceTask。

第14步:ReduceTask向MapTask获取相应分区的数据。

第15步:程序运行完毕后,MR会向RM申请注销自己。

(5)进度和状态更新

YARN中的任务将其进度和状态(包括counter)返回给应用管理器, 客户端每秒(通过mapreduce.client.progressmonitor.pollinterval设置)向应用管理器请求进度更新, 展示给用户。

(6)作业完成

除了向应用管理器请求作业进度外, 客户端每5秒都会通过调用waitForCompletion()来检查作业是否完成。时间间隔可以通过mapreduce.client.completion.pollinterval来设置。作业完成之后, 应用管理器和Container会清理工作状态。作业的信息会被作业历史服务器存储以备之后用户核查。

四、资源调度器

先进先出调度器(FIFO)

FIFO Scheduler 把应用按提交的顺序排成一个队列,这是一个先进先出队列,在进行资源分配的时候,先给队列中最头上的应用进行分配资源,待最头上的应用需求满足后再给下一个分配,以此类推。FIFO Scheduler 是最简单也是最容易理解的调度器,也不需要任何配置,但它并不适用于共享集群。大的应用可能会占用所有集群资源,这就导致其它应用被阻塞。在共享集群中,更适合采用 Capacity Scheduler 或 FairScheduler,这两个调度器都允许大任务和小任务在提交的同时获得一定的系统资源。

工作方法:

  • 单队列

  • 先进先出原则

缺点:FIFO Scheduler是最简单也是最容易理解的调度器,也不需要任何配置,但它并不适用于共享集群。大的应用可能会占用所有集群资源,这就导致其它应用被阻塞,比如有个大任务在执行,占用了全部的资源,再提交一个小任务,则此小任务会一直被阻塞。

容量调度器(Capacity Scheduler)

调度器允许多个组织共享整个集群,每个组织可以获得集群的一部分计算能力。通过为每个组织分配专门的队列,然后再为每个队列分配一定的集群资源,这样整个集群就可以通过设置多个队列的方式给多个组织提供服务了。除此之外,队列内部又可以垂直划分,这样一个组织内部的多个成员就可以共享这个队列资源了,在一个队列内部,资源的调度是采用的是先进先出(FIFO)策略。

特点
  • 灵活性:如果一个队列中的资源有剩余,可以暂时共享哪些需要资源的队列,而一旦该队列有新的应用程序提交,则其他队列释放的资源会归还给该队列,这种资源灵活分配的方式可以明显提高资源利用率。

  • 容量保障:管理员可以为每一个队列设置资源最低保障和资源使用上限,而所有提交到该队列的应用程序共享这些资源。

  • 多冲租赁:支持多用户共享集群和多应用程序同时运行,为防止单个应用程序、用用户或者队列独占集群中的资源,管理员可为之增加多重约束(比如单个用用程序同时运行的任务数量等等)

  • 安全保证:每一个队列有严格的ACL队列规定它访问的用户,每一个用户可以指定哪些用户允许查看自己应用程序的运行状态或者控制运行程序(比如杀死应用程序)。此外,管理员可以指定队列管理员和集群系统管理员。

  • 动态更新配置文件:管理员可以根据动态修改各种配置参数,实现在线集群管理。

工作方法
  • 多队列

  • 资源使用量最小、优先级高的先执行

  • 在多用户的情况下,可以最大化集群的吞吐量和利用率

公平调度器(FairScheduler)

Fair调度器的设计目标是为所有的应用分配公平的资源,当然,公平调度在也可以在多个队列间工作。可以解决小任务在合理时间内完成。举个例子,假设有两个用户A和B,他们分别拥有一个队列。当A启动一个job而B没有任务时,A会获得全部集群资源;当B启动一个job后,A的job会继续运行,不过一会儿之后两个任务会各自获得一半的集群资源。如果此时B再启动第二个job并且其它job还在运行,则它将会和B的第一个job共享B这个队列的资源,也就是B的两个job会用于四分之一的集群资源,而A的job仍然用于集群一半的资源,结果就是资源最终在两个用户之间平等的共享。

与容量调度器的不同
(1)资源公平共享

在每一个队列中,FairScheduler可以选择按照FIFO、Fair策略为应用程序分配资源。其中,Fair策略(默认)是一种基于最大最小公平算法实现的资源多路复用方式。默认情况下,每隔队列内部采用该方式分配资源。这意味着,如果一个队列中有两个应用程序同时运行,每个应用程序可得到1/2的资源;如果三个应用程序同时运行,则每个应用程序可以得到1/3的资源。

(2)支持资源抢占

当某个队列中有剩余资源是,调度器会将这些资源共享给其他队列,而当该队列中有新的应用程序提交时,调度器要为它收回资源。为了尽可能降低不不要的计算浪费,调度器采用了先等待后强制收回的策略,即如果等待一段时间后尚未归还的资源,则会进行资源抢占;从哪些超额使用资源的队列中杀死一部分任务,从而释放资源。

yarn.scheduler.fair.preemption=true 如果该配置开启资源抢占。

(3)负载均衡

FairScheduler提供了一个基于任务数目的负载均衡机制。该机制尽可能将系统中的任务均匀分配到各个节点上。此外,用火狐可以根据自己的需要设计负载均衡机制。

(4)调度策略配置灵活

FairScheduler允许管理员为每个队列单独设置调度策略(当前支持FIFO,Fair或DRF三种)。

(5)提高小应用程序响应时间

由于采用了最大最小公平算法。小作业可以快速获取资源并运行完成。

工作方法
  • 多队列

  • 公平调度,所有任务具有相同的资源

五、资源调度器的配置

在yarn-default.xml文件中有这个配置项

   <property>
     <description>The class to use as the resource scheduler.</description>
     <name>yarn.resourcemanager.scheduler.class</name>                    <value>org.apache.hadoop.yarn.server.resourcemanager.scheduler.capacity.CapacityScheduler</value>
   </property>

配置集群队列

调度器默认就1个default队列,如图

修改capacity-scheduler.xml文件内容

   <!--设置两个队列 一个队列的名字叫做defalut,另外一个叫做secondqueue-->
   <property>
     <name>yarn.scheduler.capacity.root.queues</name>
     <value>default,secondqueue</value>
     <description>
       The queues at the this level (root is the root queue).
     </description>
   </property>
   <!--两个队列占整个root队列的占比都是百分之五十-->
   <property>
     <name>yarn.scheduler.capacity.root.default.capacity</name>
     <value>50</value>
     <description>Default queue target capacity.</description>
   </property>
 ​
   <property>
     <name>yarn.scheduler.capacity.root.secondqueue.capacity</name>
     <value>50</value>
     <description>Default queue target capacity.</description>
   </property>
   <!--设置两个队列的用户占用队列中资源的百分数,默认设置是百分之百-->
   <property>
     <name>yarn.scheduler.capacity.root.default.user-limit-factor</name>
     <value>1</value>
     <description>
       Default queue user limit a percentage from 0.0 to 1.0.
     </description>
   </property>
 ​
   <property>
     <name>yarn.scheduler.capacity.root.secondqueue.user-limit-factor</name>
     <value>1</value>
     <description>
       Default queue user limit a percentage from 0.0 to 1.0.
     </description>
   </property>
   <!--设置两个队列中最大可以设置为百分之七十,对于整个root队列的资源,因为这是一个弹性的资源分配-->
   <property>
     <name>yarn.scheduler.capacity.root.default.maximum-capacity</name>
     <value>70</value>
     <description>
       The maximum capacity of the default queue. 
     </description>
   </property>
 ​
   <property>
     <name>yarn.scheduler.capacity.root.secondqueue.maximum-capacity</name>
     <value>70</value>
     <description>
       The maximum capacity of the default queue.
     </description>
   </property>
 ​
   <!--设置队列的状态,是运行的状态-->
   <property>
     <name>yarn.scheduler.capacity.root.default.state</name>
     <value>RUNNING</value>
     <description>
       The state of the default queue. State can be one of RUNNING or STOPPED.
     </description>
   </property>
 ​
   <property>
     <name>yarn.scheduler.capacity.root.secondqueue.state</name>
     <value>RUNNING</value>
     <description>
       The state of the default queue. State can be one of RUNNING or STOPPED.
     </description>
   </property>
 ​
   <!--设置两个队列acl提交的用户,*表示谁都可以提交-->
   <property>
     <name>yarn.scheduler.capacity.root.default.acl_submit_applications</name>
     <value>*</value>
     <description>
       The ACL of who can submit jobs to the default queue.
     </description>
   </property>
 ​
   <property>
     <name>yarn.scheduler.capacity.root.secondqueue.acl_submit_applications</name>
     <value>*</value>
     <description>
       The ACL of who can submit jobs to the default queue.
     </description>
   </property>
 ​
   <!--表示队列中提交acl的管理者,* 默认所有人-->
   <property>
     <name>yarn.scheduler.capacity.root.default.acl_administer_queue</name>
     <value>*</value>
     <description>
       The ACL of who can administer jobs on the default queue.
     </description>
   </property>
 ​
   <property>
     <name>yarn.scheduler.capacity.root.secondqueue.acl_administer_queue</name>
     <value>*</value>
     <description>
       The ACL of who can administer jobs on the default queue.
     </description>
   </property>
 ​
   <!--设置 显示那些人配置过这些队列的信息 -->
   <property>
     <name>yarn.scheduler.capacity.root.default.acl_application_max_priority</name>
     <value>*</value>
     <description>
       The ACL of who can submit applications with configured priority.
       For e.g, [user={name} group={name} max_priority={priority} default_priority={priority}]
     </description>
   </property>
 ​
   <property>
     <name>yarn.scheduler.capacity.root.secondqueue.acl_application_max_priority</name>
     <value>*</value>
     <description>
       The ACL of who can submit applications with configured priority.
       For e.g, [user={name} group={name} max_priority={priority} default_priority={priority}]
     </description>
   </property>
 ​
   <!--表示队列中的job运行的最大存活时间,-1表示可以一直存活-->
    <property>
      <name>yarn.scheduler.capacity.root.default.maximum-application-lifetime
      </name>
      <value>-1</value>
      <description>
         Maximum lifetime of an application which is submitted to a queue
         in seconds. Any value less than or equal to zero will be considered as
         disabled.
         This will be a hard time limit for all applications in this
         queue. If positive value is configured then any application submitted
         to this queue will be killed after exceeds the configured lifetime.
         User can also specify lifetime per application basis in
         application submission context. But user lifetime will be
         overridden if it exceeds queue maximum lifetime. It is point-in-time
         configuration.
         Note : Configuring too low value will result in killing application
         sooner. This feature is applicable only for leaf queue.
      </description>
    </property>
 ​
   <property>
     <name>yarn.scheduler.capacity.root.secondqueue.maximum-application-lifetime
     </name>
     <value>-1</value>
     <description>
       Maximum lifetime of an application which is submitted to a queue
       in seconds. Any value less than or equal to zero will be considered as
       disabled.
       This will be a hard time limit for all applications in this
       queue. If positive value is configured then any application submitted
       to this queue will be killed after exceeds the configured lifetime.
       User can also specify lifetime per application basis in
       application submission context. But user lifetime will be
       overridden if it exceeds queue maximum lifetime. It is point-in-time
       configuration.
       Note : Configuring too low value will result in killing application
       sooner. This feature is applicable only for leaf queue.
     </description>
   </property>
   <!-- 默认的存活时间 -->
    <property>
      <name>yarn.scheduler.capacity.root.default.default-application-lifetime
      </name>
      <value>-1</value>
      <description>
         Default lifetime of an application which is submitted to a queue
         in seconds. Any value less than or equal to zero will be considered as
         disabled.
         If the user has not submitted application with lifetime value then this
         value will be taken. It is point-in-time configuration.
         Note : Default lifetime can't exceed maximum lifetime. This feature is
         applicable only for leaf queue.
      </description>
    </property>
 ​
   <property>
     <name>yarn.scheduler.capacity.root.secondqueue.default-application-lifetime
     </name>
     <value>-1</value>
     <description>
       Default lifetime of an application which is submitted to a queue
       in seconds. Any value less than or equal to zero will be considered as
       disabled.
       If the user has not submitted application with lifetime value then this
       value will be taken. It is point-in-time configuration.
       Note : Default lifetime can't exceed maximum lifetime. This feature is
       applicable only for leaf queue.
     </description>
   </property>

注:如果是通过java写的API接口打包成jar包的形式,而想指定队列进行运行,需要在设置conf之后加上指定的队列名。

 // 1、创建配置对象
 Configuration conf=new Configuration();
 // 指定在哪一个队列中运行
 conf.set("mapreduce.job.queuename","secondqueue");

六、任务的推测执行

一个作业由若干个map任务·和reduce任务组成,因为硬件的老化和软件bug等因素,会导致某些任务运行缓慢。当发现拖后腿的任务时,比如某个任务的运行速度远慢于平均速度;就位拖后腿的任务启动一个备份任务,同时运行。谁先运行完就采用谁的结果。

执行推测任务的前提条件 1、每个Task只能有一个备份任务 2、当前job已完成的Task进度不少于5% 3、开启推测执行参数。(mapred-site.xml默认是开启的)

 <property>
     <name>mapreduce.map.speculative</name>
     <value>true</value>
     <description>If true,then multilpe instances of some map tasks may be exexcuted parallel.</description>
 </property>

不能使用推测执行机制的条件限制 1、任务间存在严重的负载倾斜(比如一个任务量10g;一个任务量1g) 2、一些特殊任务(比如向数据库中写数据)

推测执行算法原理 假设某一时刻,任务T的执行进度为progress,则可通过一定的算法推测出任务的最终完成时刻estimateEndTime。如果此时为该任务启动一个备份任务,则可推断出它可能的完成时刻estimateEndTime*。

 estimateRunTime =(currentTimestamp - taskStartTime)/ progress
 ​
 推测运行时间(60s)=( 当前时刻(6)- 任务启动时刻(0))/ 任务运行比例(10%)
 ​
 estimateEndTime = estimateRunTime + taskStartTime
 ​
 推测执行完成时刻60 = 推测运行时间(60s) + 任务启动时刻(0)
 estimateEndEndTime* = currentTimestamp + averageRunTime
 ​
 备份任务推测完成时刻(16) = 当前时刻(6) + 运行完成任务的平均时间(10s)

MR总是选择差值最大的任务(estimateEndTime - estimateEndTime*),并为之启动备份任务。 为了防止大量任务同时启动备份任务造成的资源浪费,MR为每个作业设置了同时启动的备份任务数目上限。 推测执行机制实际采用了经典的优化算法:以空间换时间,它同时启动多个相同的任务处理相同的数据,并让这些任务相互竞争以缩短数据处理时间;对这种机制会占用较多的计算资源,所以在集群资源紧缺的情况下,应合理使用该机制,争取在多用少量计算资源的情况下,减少作业的计算时间。

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值