基于本文回答

播面 播面

文图音视,全方位拆解八股文
0
评论

任务在 Container 中运行结束后,资源是如何被回收和释放的?

知识点图片

在 Apache YARN 中,当一个任务在 Container 中运行结束后,资源的回收和释放是一个涉及 操作系统底层清理节点级状态更新集群级资源重新调度 的多步协同过程。

整个过程主要由 NodeManager (NM)(负责节点本地的物理清理)和 ResourceManager (RM)(负责集群全局的逻辑记账)以及 ApplicationMaster (AM)(负责应用级管理)共同完成。

以下是资源回收和释放的详细过程:

1. 任务进程退出与状态上报

  • 进程结束: Container 内的任务进程(例如 MapReduce 的一个 Map Task,或 Spark 的一个 Executor)执行完毕,无论是正常退出(Exit code 0)还是异常退出(非 0),操作系统级别的进程结束。
  • AM 感知: 任务在退出前,通常会向该应用的 ApplicationMaster (AM) 发送最后的状态报告,告知任务已完成。
  • NM 监控感知: NodeManager 内部有一个组件叫 ContainerMonitor,它通过轮询操作系统(如读取 /proc 目录)或依赖操作系统的信号机制,感知到该 Container 的主进程及其子进程已经结束。

2. NodeManager 执行本地物理清理 (物理资源释放)

当 NM 确认 Container 结束后,会调用 ContainerExecutor(通常是 DefaultContainerExecutorLinuxContainerExecutor)执行本地物理资源的回收:

  • 清理残留进程(防内存泄漏):
    • NM 会查找该 Container 衍生出的所有子进程(通过进程树 Process Tree Tracking)。
    • 如果还有残留进程,NM 会发送 SIGTERM 信号,等待一小段时间后发送 SIGKILL 信号,确保该 Container 产生的所有进程都被彻底杀死,释放占用的 CPU 和内存。
  • Cgroups 资源解绑(如果开启):
    • 如果集群配置了 LinuxContainerExecutor 并开启了 Cgroups(Control Groups),NM 会将该 Container 对应的 Cgroup 目录删除。
    • 删除 Cgroup 会立即解除对该 Container 的 CPU 份额、内存上限的硬隔离限制,操作系统将这些硬件资源收回。
  • 清理本地磁盘文件:
    • NM 会清理该 Container 在本地磁盘(yarn.nodemanager.local-dirs)上产生的工作目录、临时文件、下载的依赖 Jar 包(如果没有其他 Container 共享的话)和缓存。
  • 日志处理(Log Aggregation):
    • 如果开启了日志聚集功能,NM 会将该 Container 在本地(yarn.nodemanager.log-dirs)产生的日志收集并上传到 HDFS,随后删除本地日志文件以释放磁盘空间。

3. ApplicationMaster 向 ResourceManager 发送释放请求

  • AM 知道任务完成后,会在下一次与 ResourceManager (RM) 的 心跳(Heartbeat) 中,携带一个 ReleaseContainersRequest(释放 Container 请求)。
  • 这告诉 RM:“我不再需要这个 Container 了,请把它从我的应用资源配额中扣除”。

4. NodeManager 向 ResourceManager 汇报状态

  • NodeManager 也会在与 ResourceManager 的周期性 心跳 中,将该 Container 的状态更新为 COMPLETE(已完成)。
  • 此时,RM 会验证这个信息。

5. ResourceManager 更新全局视图 (逻辑资源释放)

ResourceManager 中的 ResourceScheduler(如 Capacity Scheduler 或 Fair Scheduler)接收到 NM 的心跳和 AM 的释放请求后,执行逻辑上的资源回收:

  • 账本更新: RM 会在内存的资源账本中,将该 Container 占用的资源(如 <Memory: 2GB, vCores: 1>)从该节点(Node)的已用资源中扣除,并加回到该节点的可用资源池中。
  • 队列额度更新: 同时,RM 会将这些资源从该应用所在的队列(Queue)的已用额度中扣除。
  • 触发重新调度: 资源被释放回可用池后,RM 的调度器会立刻被触发。它会检查当前是否有其他等待运行的 Application 或 Container 请求,并将刚刚释放的资源分配给下一个最需要(优先级最高/最饿)的任务。

补充场景:非正常结束的资源回收

除了任务正常跑完,还有几种情况会触发上述回收流程:

  1. OOM (Out of Memory) 被杀: 如果 Container 实际使用的内存超过了 YARN 申请的上限,NM 的监控线程会主动 Kill 掉该进程树(或者触发了 Linux 内核的 OOM Killer)。之后走相同的清理流程。
  2. 被 RM 抢占 (Preemption): 当集群资源紧张时,RM 可能会为了保证高优先级队列的资源,主动命令 NM 杀掉某些低优先级队列正在运行的 Container。
  3. AM 崩溃/结束: 如果整个 ApplicationMaster 运行结束或崩溃,RM 会立刻下令各个 NM 杀掉该应用下的所有 Container,并强行回收所有资源。
00:00
00:00