6.4.4 作业和任务状态转换图
在Hadoop MapReduce中,作业和任务是有生命周期的,它们的状态受各种行为的影响而发生变化。在本小节中,我们将分析作业和任务涉及的状态转移以及导致状态转移的事件。
(1)作业状态转换图
前面提到,作业的运行时信息由JobInProgress类进行监控和维护,因此,作业状态转移也由该类进行更新。在Hadoop中,一个作业在运行过程中可能涉及所有可能的状态转移,如图6-4所示。
图 6-4 作业状态转换图
图6-4中涉及的状态转换以及对应事件如下。
❑PREP→RUNNING:作业的Setup Task(job-setup Task)成功执行完成。
❑RUNNING→SUCCEEDED:作业的Cleanup Task(job-cleanup Task)执行成功。
❑PREP→FAILED/KILLED:人为使用Shell命令杀死作业,即bin/hadoop job[-kill|-fail]<jobid>。
❑RUNNING→FAILED:多种情况可导致该状态转移,包括人为使用Shell命令杀死作业(使用“bin/hadoop job-fail<jobid>”命令),作业的Cleanup/Setup Task运行失败和作业失败的任务数超过了一定比例。
❑RUNNING→KILLED:人为使用Shell命令杀死作业,比如使用“bin/hadoop job-kill<jobid>”命令。
(2)任务状态转换图
在Hadoop中,一个任务的状态变化可能发生在JobTracker端或者TaskTracker端。总结起来,一个任务在运行过程中可能涉及所有可能的状态转移,如图6-5所示。
图 6-5 任务状态转换图
图6-5中涉及的状态转换以及对应事件如下。
❑UNASSIGNED→RUNNING:任务初始化状态为UNASSIGNED,当JobTracker将任务分配给某个TaskTracker后,该TaskTracker会为它准备运行环境并启动它,之后该任务进入RUNNING状态。
❑RUNNING→COMMIT_PENDING:该状态转换存在于产生最终结果的任务(Reduce Task或者map-only类型作业[1]的Map Task)中,当任务处理完最后一条记录后进入COMMIT_PENDING状态,以等待JobTracker批准其提交最后结果。
❑RUNNING→SUCCEEDED:该状态转换只存在于Map Task(且这些Map Task的结果将被Reduce Task进一步处理)中,当Map Task处理完最后一条记录后便意味着任务运行成功。
❑RUNNING/COMMIT_PENDING→KILLED_UNCLEAN:TaskTracker收到来自JobTracker的KillTaskAction命令后,会将对应任务由RUNNING/COMMIT_PENDING状态转化为KILLED_UNCLEAN状态,通常产生的场景是人为杀死任务,同一个TIP的多个同时运行的Task Attempt中有一个成功运行完成而杀死其他Task Attempt, TaskTracker因超时导致其上所有任务状态变为KILLED_UNCLEAN等。
❑RUNNING/COMMIT_PENDING→FAILED_UNCLEAN:多种情况下会导致该状态转移,包括本地文件读写错误、Shuffle阶段错误、任务在一定时间内未汇报进度(从而被TaskTracker杀掉)、内存使用量超过期望值或者其他运行过程中出现的错误。
❑UNASSIGNED→FAILED/KILLED:人为杀死任务。
❑KILLED_UNCLEAN/FAILED_UNCLEAN→FAILED/KILLED:一旦任务进入KILLED_UNCLEAN/FAILED_UNCLEAN状态,接下来必然进入FAILED/KILLED状态,以清理已经写入HDFS上的部分结果。
❑SUCCEEDED→KILLED:一个TIP已有一个Task Attempt运行完成,而备份任务也汇报成功,则备份任务将被杀掉或者用户人为杀死某个Task,而TaskTracker刚好汇报对应Task执行成功。
❑SUCCEEDED/COMMIT_PENDING→FAILED:Reduce Task从Map Task端远程读取数据时,发现数据损坏或者丢失,则将对应Map Task状态标注为FAILED以便重新得到调度。
[1]Map-only类型作业是指只有Map Task而没有Reduce Task的作业。对于这种作业,Map Task直接将结果写到HDFS上。