1. YARN 개요
YARN은 클러스터의 CPU·메모리를 관리하고 애플리케이션에 컨테이너 단위로 배정해 주는 자원 관리자임
1.1 YARN의 역할
- 정식 명칭 : Yet Another Resource Negotiator이며 Hadoop 2.0부터 포함된 구성 요소임
- 자원 배정 : 애플리케이션이 "코어 4개, 메모리 8GB 컨테이너 10개"를 요청하면 여유 있는 노드를 골라 배정함
- 작업 처리는 하지 않음 : 계산은 Spark 같은 프로그램이 컨테이너 안에서 수행하고 YARN은 자원 배정과 관리만 담당함
- 범용 관리자 : Spark 전용이 아니라 Hive, MapReduce 등 여러 프레임워크가 같은 클러스터를 공유함
프론트엔드의 패키지 매니저 yarn(npm 대체 도구)과는 이름만 같고 전혀 다른 것임
1.2 비유
| 호텔 |
YARN |
| 프런트(예약·배정 담당) |
ResourceManager |
| 각 층의 객실 관리 직원 |
NodeManager |
| 객실 |
컨테이너 (CPU·메모리 묶음) |
| 투숙객 |
Spark 같은 애플리케이션 |
2. 노드 구성
YARN 클러스터는 ResourceManager 노드와 NodeManager 노드가 모여서 구성됨
2.1 노드와 데몬
| 노드 종류 |
돌고 있는 YARN 프로그램 |
역할 |
| ResourceManager 노드 |
ResourceManager |
클러스터 전체 자원을 보고 배정을 결정함 |
| NodeManager 노드 |
NodeManager |
자기 서버의 자원을 관리하고 컨테이너를 실행함 |
- 노드의 정체 : 노드는 서버(머신)이고, 그 서버에서 YARN 프로그램(데몬)이 상시 돌고 있는 상태임
- YARN 클러스터 : RM 노드와 NM 노드 전체를 묶어서 부르는 말임
- 워커 노드 : 컨테이너가 실제로 뜨는 NodeManager 노드를 가리킴
2.2 구성 예시
YARN 클러스터
+-- ResourceManager 노드 x2 (HA 구성: active 1대, standby 1대)
+-- NodeManager 노드 x6 (워커 노드)
+-- Spark History Server (종료된 작업의 UI 제공, 별도 서버)
- RM HA : RM을 2대로 두어 active가 죽으면 standby가 넘겨받음
- RM UI : 각 RM의 웹 화면이며 기본 포트는 8088임
- 노드 목록 조회 : yarn node -list에는 NodeManager 노드만 나오며 RM 노드는 컨테이너가 뜨는 곳이 아니라서 목록에 없음
3. 핵심 구성 요소
ResourceManager, NodeManager, ApplicationMaster, Container 네 가지로 동작함
3.1 구성 요소별 역할
| 구성 요소 |
위치 |
역할 |
| ResourceManager (RM) |
마스터 노드 |
클러스터 전체 자원을 관리하고 컨테이너를 할당함 |
| NodeManager (NM) |
워커 노드 |
노드의 컨테이너를 실행하고 사용량을 모니터링함 |
| ApplicationMaster (AM) |
컨테이너 내부 |
애플리케이션별로 하나씩 뜨며 RM에 자원을 요청하고 작업을 조율함 |
| Container |
워커 노드 |
CPU·메모리가 할당된 실행 단위 |
3.2 ResourceManager 내부
- Scheduler : 큐 정책에 따라 컨테이너를 할당하며 작업 모니터링은 하지 않음
- ApplicationsManager : 애플리케이션 제출을 받고 첫 번째 컨테이너(AM)를 띄우며 AM 실패 시 재시작을 담당함
4. 컨테이너
컨테이너는 YARN이 노드의 자원 일부를 잘라서 내어준 실행 단위임
4.1 컨테이너의 정체
- 정확한 명칭 : YARN Container이며 YARN이 배정한 결과물이지 YARN 자체는 아님
- 실체 : 자원(CPU·메모리)을 배정받은 JVM 프로세스임
- Docker와의 차이 : 기본적으로 Docker 이미지 기반 컨테이너가 아니라서 이미지 개념 없이 노드에 설치된 환경으로 실행됨
- 노드와의 관계 : NodeManager 노드 한 대 안에 컨테이너가 여러 개 뜸
4.2 안에서 도는 것에 따른 구분
| 부르는 이름 |
안에서 도는 것 |
설명 |
| AM 컨테이너 |
ApplicationMaster |
애플리케이션마다 가장 먼저 뜨는 컨테이너 |
| 익스큐터 컨테이너 |
Spark Executor |
실제 태스크를 처리하며 보통 여러 개가 뜸 |
- 컨테이너 ID : container_<클러스터ts>_<appId>_<시도번호>_<순번> 형식이며 끝이 000001인 컨테이너가 AM 컨테이너임
컨테이너는 YARN의 구성 요소가 아니라 YARN이 할당한 자원 단위이고, 그 안에서 실제로 실행되는 것은 Spark 같은 애플리케이션임
5. Spark와 YARN의 관계
YARN 모드에는 Spark 전용 노드가 없고 Spark는 컨테이너 안에서 실행됨
5.1 Spark의 위치
| Spark 구성 요소 |
뜨는 위치 |
| 익스큐터 |
익스큐터 컨테이너 안 (항상) |
| 드라이버 (cluster 모드) |
AM 컨테이너 안 |
| 드라이버 (client 모드) |
컨테이너가 아니라 spark-submit을 실행한 머신 |
- 상시 구동 아님 : 제출할 때마다 YARN이 컨테이너를 배정하고 그 안에서 Spark 프로세스가 시작되며 작업이 끝나면 함께 종료됨
- Standalone과의 차이 : Standalone은 Spark Master/Worker 데몬이 상시 돌지만 YARN에는 그런 데몬이 없음
- Spark 설치 위치 : spark-submit을 실행하는 클라이언트 노드에만 있으면 되고 실행에 필요한 jar는 제출 시 컨테이너로 전달됨
5.2 구조도
spark-submit (cluster 모드)
|
v
[ResourceManager] 자원 배정 결정
|
v
NodeManager 노드
+-- AM 컨테이너 -> Spark Driver 실행
+-- 익스큐터 컨테이너 -> Spark Executor 실행
+-- 익스큐터 컨테이너 -> Spark Executor 실행
5.3 실행 흐름
- spark-submit으로 제출하면 RM이 애플리케이션을 등록함
- RM이 NodeManager 한 곳에 첫 컨테이너를 배정하고 AM이 실행됨
- cluster 모드에서는 Spark 드라이버가 AM 안에서 실행됨
- AM이 RM에 익스큐터용 컨테이너를 추가로 요청함
- 각 NodeManager에서 익스큐터가 실행되어 태스크를 처리함
- 작업이 끝나면 컨테이너가 반환되고 프로세스도 함께 사라짐
6. 소스코드와 데이터의 이동
소스코드는 컨테이너 시작 전에 내려받고 데이터는 실행 중에 직접 읽음
6.1 소스코드 전달
- localization : NodeManager가 컨테이너를 시작하기 전에 필요한 파일(main.py, 설정, 의존성)을 HDFS에서 노드 로컬 디스크로 내려받는 과정임
- HDFS 경로로 제출한 경우 : 메인 파일을 hdfs:// 경로로 지정하면 NodeManager가 해당 파일을 내려받아 실행함
- 로컬 파일로 제출한 경우 : spark-submit이 HDFS의 임시 스테이징 경로에 먼저 올리고 이후 같은 방식으로 내려받음
- 코드 갱신 시 주의 : 제출 시점에 코드를 내려받으므로 HDFS의 코드를 바꿔도 이미 실행 중인 작업에는 반영되지 않고 재시작해야 함
6.2 구분
| 구분 |
대상 |
방식 |
| 소스 코드 |
실행할 코드 |
NodeManager가 컨테이너 시작 전에 로컬로 내려받음 |
| 입력 데이터 |
처리할 데이터 |
익스큐터가 실행 중에 HDFS DataNode에서 직접 읽음 |
| 출력 데이터 |
처리 결과 |
익스큐터가 HDFS에 직접 씀 |
제출 머신은 요청만 보내고, RM이 정한 워커 노드의 NodeManager가 HDFS에서 소스를 내려받아 컨테이너로 실행함
7. 구조 확인 방법
노드, 컨테이너, Spark 프로세스 순서로 확인함
7.1 단계별 확인
yarn node -list -all
yarn application -list -appStates RUNNING
yarn container -list <applicationAttemptId>
jps -m
- yarn node -list -all : NodeManager 노드 목록과 상태, 노드별 컨테이너 수를 확인함
- yarn application -list : 실행 중인 애플리케이션과 ID를 확인함
- yarn container -list : 컨테이너가 어느 노드에 떠 있는지 확인함
- jps -m : 컨테이너가 뜬 노드에서 실행하며 ApplicationMaster, CoarseGrainedExecutorBackend 프로세스가 보임
7.2 Spark UI 활용
- Executors 탭 : 드라이버와 익스큐터가 어느 호스트에서 도는지 한 화면에 나옴
- 드라이버 호스트가 NodeManager 노드 중 하나면 : cluster 모드
- 드라이버 호스트가 제출한 머신이면 : client 모드
- 종료된 작업 : Spark History Server에서 같은 화면을 볼 수 있음
요약
| 항목 |
핵심 내용 |
| YARN |
클러스터 자원을 컨테이너 단위로 배정하는 자원 관리자 |
| 노드 |
RM 노드(배정 결정)와 NM 노드(컨테이너 실행, 워커 노드)가 모여 YARN 클러스터를 이룸 |
| 컨테이너 |
YARN이 노드 자원 일부를 잘라 내어준 JVM 프로세스 단위 |
| Spark의 위치 |
전용 노드 없이 컨테이너 안에서 실행되고 작업이 끝나면 사라짐 |
| 소스 전달 |
NodeManager가 컨테이너 시작 전에 HDFS에서 내려받음 |
| 확인 방법 |
yarn node -list, yarn container -list, jps -m, Spark UI Executors 탭 |
YARN은 노드(서버)들이 모여 컨테이너를 배정하는 구조이고, Spark는 그 컨테이너 안에서 제출할 때마다 실행되었다가 종료되는 프로그램임