ABOUT ME

-

Today
-
Yesterday
-
Total
-
  • HDFS(하둡분산파일시스템) 주요 개념 및 아키텍쳐
    Data 2021. 1. 20. 18:18
    반응형

    HDFS는 하둡 환경에서 분산 파일 시스템 기능을 담당하는 하둡의 주요 모듈입니다. 이번 글에서는 HDFS와 관련해 다음과 같은 부분들을 다루고자 합니다:

     

     

    관련글:


    HDFS는 기존 파일시스템과 다른 점으로 인해 처음 접하시는 분들이라면 익숙하지 않을 개념들이 있습니다. 주요한 개념들의 정의를 살펴보며, 대략적인 아키텍쳐에 대해 전달해보고자 합니다.

     

    블록 (Blocks)

    디스크는 데이터가 읽히고 쓰여질 수 있는 가장 작은 단위인 블록을 가집니다. 한 개의 디스크에 기반한 파일시스템은 디스크 블록의 몇 배가 되는 '파일시스템 블록'을 처리하며 데이터를 입출력합니다. 파일시스템 블록은 보통 몇 킬로바이트인 반면에, 디스크 블록은 대부분 512 바이트입니다. 이러한 부분은 데이터를 읽고 쓰는 파일시스템 사용자는 대부분 알고 있는 부분이나, 파일시스템의 운영유지를 위해 df, fsck와 같은 명령어를 통해 파일시스템 블록 레벨에서 작업하는 부분에 익숙한 사용자는 드뭅니다.

     

    HDFS도 블록이라는 개념을 가지나, (디폴트) 128 MB로 매우 큽니다. 위의 파일시스템에서의 파일과 마찬가지로, HDFS의 파일도 블록 크기의 덩어리로 나뉘어 (replication 설정에 따라 여러 노드에 중복되어 저장되고) 독립적인 단위로 저장됩니다. 하지만 HDFS의 파일은 파일 사이즈가 블록 사이즈보다 작아도 블록 크기를 모두 차지 하지 않습니다. 

     

    분산파일시스템에서 블록이라는 개념은 1) 하나의 파일이 하나의 디스크를 넘는 크기를 가질 수 있음, 2) 저장소 서브시스템 관리는 단순화 함 (블록은 크기가 같아 각 디스크에 몇 개가 존재하는지 파악이 쉬움, 블록은 permission과 같은 부분은 신경쓸 필요가 없이 단순하게 데이터 덩어리만 가지고 있게함), 3) 실패 시 데이터 복구를 위한 replication 구현 및 운영 시 잘 부합함 등의 장점을 가져다 줍니다.

     

    Replication

    데이터 복제는 HDFS가 Fault-tolerant가 가능하도록 하는 주요 개념입니다. 파일 단위로 Replication Factor를 설정할 수 있는데, 이 설정에 따라 HDFS는 해당 파일의 블록들을 N번(디폴트 3) 복제하여 저장합니다.

     

    이러한 블록 복제로 한 개의 파일을 이루는 각 블록이 여러 노드에 저장되어 있기에 해당 파일 읽기 시에 가장 가까운 노드로부터 읽어오게하여 최적화를 하기도 합니다. 

     

    예로, 아래와 같이 하나의 파일이 2개의 블록으로 구성된다면, 개별 블록은 Replication Factor 3가 3이라고 할 때 아래와 같이 데이터노드에 복제되어 저장됩니다:

     

     

    Image from Author

     

    네임노드와 데이터노드 (Namenode and Datanode)

    HDFS 운영 시의 간략한 구조와 어떤 정보가 오고가는지 그려보면 아래와 같습니다 [1]:

    Image from Author inspired by [1]

    HDFS 클러스터는 마스터-슬레이브 구조로 2가지 형태의 노드(클러스터의)를 가집니다: 네임노드와 데이터노드. 아래에서는 네임노드 및 데이터노드에 접근하는 클라이언트를 포함하여 각 노드가 어떻게 작동하는지와 서로 간의 관계를 살펴보겠습니다 (이러한 구조는 대부분의 분산 파일 시스템 - PVFS, Lustre, GFS - 에서 존재합니다 [8]). 

     

    좀 더 상세한 기능에 대한 부분은 마지막의 '네임노드와 데이터노드의 구체적인 기능들'에서 다루도록 하겠습니다.

     

    네임노드

    네임노드는 파일시스템의 네임스페이스를 관리하며 파일시스템의 트리와 트리에 존재하는 모든 파일과 디렉토리를 다룹니다. 이러한 정보(네임스페이스, 접근권한정보 파일 - 블록 매핑 등)는 네임노드가 존재하는 로컬 파일시스템의 '네임스페이스 이미지' 및 'edit 로그'라는 2가지 형태로 영속적으로 저장됩니다. 또한, 네임노드는 어떤 파일을 구성하는 블록들이 어느 데이터노드에 저장되어 있는지 알고 있으나, 이러한 사항은 재실행 시 데이터노드로부터 재구성할 수 있기 때문에 영속적으로 저장하진 않습니다.

     

    데이터노드

    데이터노드는 파일시스템의 실제 저장 노드로 블록을 요청을 받았을 때 블록을 저장, 삭제, 송신하고 가지고 있는 블록 리스트를 네임노드에 주기적으로 보고합니다 (block report 라고 불림). 

     

    클라이언트

    클라이언트는 사용자(또는 HDFS 사용 애플리케이션)를 대신해 네임노드 및 데이터노드와 통신합니다. 클라이언트는 사용자에게 POSIX와 유사한 형태의 filesystem interface를 제공하기에, 사용자 코드는 네임노드 및 데이터노드에 대해 인지하지 않고 정해진 API를 통해 접근할 수 있습니다. 

     

    클라이언트-네임노드

    특정 커맨드(읽기, 쓰기, 삭제 등) 실행 시 클라이언트는 가장 먼저 네임노드와 통신합니다. 요청한 리소스에 대한권한은 가지고 있는지 확인, 파일에 해당되는 블록은 무엇이고 블록은 어떤 데이터 노드에 위치해 있는지 확인, Write할 파일을 데이터를 채워넣기 전에 생성 등을 위해 통신하게 됩니다. 

     

    클라이언트-데이터노드

    클라이언트는 기본적으로 데이터노드와 같은 기기에 있거나(local) 또는 다른 기기에 존재(remote)하는 경우에 따라 데이터노드와 다르게 통신합니다. 그렇지만 읽고자 하거나, 쓰고자 하는 파일의 데이터는 모두 클라이언트-데이터노드 간의 통신을 통해서 이뤄지게 됩니다 (위 이미지의 두꺼운 검은색). 

     

    블록 캐싱

    보통 데이터노드는 블록을 디스크에서 읽어보지만, 빈번하게 사용되는 블록의 경우 명시적으로 'off-heap block cache'에 캐싱할 수 있습니다. 캐싱이 enabled되면 디폴트로 1개의 데이터노드에 블록이 캐싱되지만, (파일 단위인) 설정을 통해 여러 노드에도 캐싱할 수 있습니다. 

     

    Federation

    Namenode and Datanode Structure - Image from Author inspired by [6]

     

    네임노드가 모든 파일, 블록, 디렉토리의 정보를 메모리에 저장하기에 매우 큰 클러스터에서는 네임노드 메모리가 병목이 되었습니다. 2.x 버젼에서 도입된 HDFS Federation은 이러한 문제에 대한 해결책으로 하나의 네임노드가 파일시스템의 일부분만 관리하도록 블록풀(Block Pool)을 추가해줍니다(예로, 하나는 /user 서브 path만, 하나는 /share만 담당).

     

    그러한 블록풀은 하나의 네임스페이스에 속하는 블록들의 모음입니다. 데이터노드는 클러스터에 존재하는 모든 블록풀들을 위한 블록들을 저장합니다. 그리고 개별 블록풀은 독립적으로 관리되기에 다른 네임스페이스와 관련없이 새로운 블록을 생성하고 변경할 수 있습니다. 

     

     

    네임스페이스와 블록풀은 합쳐서 '네임스페이스 볼륨'이라는 명칭으로

    불리고 관리됩니다. 하나의 네임스페이스가 삭제되면 그에 대응하는 블록풀도 데이터노드에서 삭제됩니다. 

     

     

     

     

     

    HDFS High Availability

    네임노드 메타데이터를 다른 파일시스템으로 복제해두거나 체크포인트 생성을 위한 2번째 네임노드(secondary)를 사용하는 것은 데이터 손실을 막아주지만 파일시스템의 HA(High Availability)를 보장해주지는 않습니다. 네임노드는 여전히 SPOF(Single point of Failure)이기에 active했던 네임노드가 다운되면 모든 파일시스템에 기반한 서비스의 장애가 발생합니다. 

     

    위와 같은 상황에서 실패한 네임노드를 회복하기 위해서는, 운영자가 복사해둔 파일시스템 메타데이터와 같이 새로운 네임노드를 실행하고 데이터노드와 클라이언트가 이 새로운 네임노드를 사용하도록 설정해주어야 합니다. 새로운 네임노드는 1) 네임스페이스 이미지를 메모리로 로드하고, 2) edit 로그를 replay하고, 3) safe mode를 벗어나기 위해 데이터노드로부터  block report를 받고 나서야 클라이언트로부터의 요청에 응답할 수 있습니다. 대규모 클러스터에서는 30분 이상 시간이 소요되는 작업입니다.

     

    하둡 2에서는 이러한 상황의 해결책으로 HDFS 네임노드 HA를 제공합니다.  Active-Standby로 구성되며 active 다운 시, standby가 바로 클라이언트 요청을 해결할 수 있습니다. 이러한 아키텍쳐는 아래와 같은 사항들이 선행되어야 가능합니다:

     

    • 네임노드들은 edit 로그를 공유하기 위해 HA가 보장되는 공유 스토리지를 사용합니다. Standby가 시작될 때, 공유된 edit  로그를 읽어 active 네임노드의 상태를 동기화하고 요청 처리를 이어갑니다.
    • 데이터노드들은 block report를 2개의 네임노드 모두에 보내어 각 네임노드의 메모리에 블록 매핑 정보가 업데이트되도록 하여야 합니다.
    • 클라이언트들 역시 active 통신 실패 시, 자동으로 standby에 접근할 수 있어야 합니다.
    • (체크포인트 생성을 위해 사용되었던) 2번째 네임노드는 standby가 대신하게 됩니다.

    HA 공유 스토리지를 위해서는 2가지 옵션이 존재합니다: NFS filer 또는 QJM(Quorum Journal Manager). QJM은 HDFS에서 구현된 것으로 edit 로그 HA를 제공하기 위한 목적으로 설계되었으며 권장되는 옵션입니다. QJM은 그룹의 저널노드들을 실행하고 edit 이벤트는 대다수의 저널노드에 write됩니다. 주로 노드 실패를 방지하기 위해 3개의 저널노드가 존재합니다 (Zookeeper와 유사, QJM은 Zookeeper를 사용하지 않으나 HDFS HA가 active 노드 electing을 위해 주로 사용함).

     

    NFS Filer based HDFS HA Structure - Image from Author inspired by [3]

    Failover와 Fencing

    Active에서 Standby로 전환하는 부분은 페일오버컨트롤러(failover controller)라는 시스템 내의 컴포넌트에 의해 진행됩니다. 다양한 페일오버컨트롤러가 있으나 디폴트로 Zookeeper를 사용합니다. 각 네임노드는 lightweight한 페일오버 컨트롤러 프로세스를 실행하고 그것은 각 네임노드의 실패를 모니터링하다가 실패 시 페일오버를 촉발합니다.

     

    Ungraceful 페일오버의 경우 실패한 네임노드가 정확히 멈췄는지 확정하는 것이 불가능합니다. 예로, active 네임노드가 살아있는데, 느린 네트워크가 페일오버를 촉발시킬 수 있습니다. HA 구현은 이와 같은 상황에 대비해 active 네임노드가 데미지를 입히거나 corruption을 발생시킬 수 없도록 많은 안전장치를 구현해 두었습니다. 그것을 fencing이라고 부릅니다.

     

    QJM은 단 하나의 네임노드만 edit 로그에 쓸 수 있게하지만, 이전의 active가 죽지않고 살아있다가 클라이언트에게 오류 값을 반환하거나 할 수 있습니다. 그렇기에 SSH fencing을 설정하여 이전 네임노드 프로세스를 죽이는 것은 매우 바람직한 일입니다. 이렇게 '강한' fencing은 주로 NFS Filer를 사용할 때 고려됩니다 (하나의 네임노드만 write하도록 강제할 수 없어서).

     

     

    Reference

    [1] The Google File System

    [2] Hadoop Definitive Guide

    [3] Hadoop Operations

    [4] HDFS Scalability: The limits to growth

    [5]  Architecting Modern Data Platform

    [6] An Introduction to HDFS Federation

    [7] A write‑friendly approach to manage namespace of Hadoop distributed file system by utilizing nonvolatile memory

    [8] The Hadoop Distributed File System

    반응형
Kaden Sungbin Cho