Pasted image 20230920173141.png

Zookeeper?

  • 분산 처리 어플리케이션을 위한 코디네이터 시스템
    • HA 구성 시 서비스간 데이터 공유, 서버 Health Check등을 해주는 역할

역할

  1. 설정 관리 (Configuration Management)

    • Cluster의 설정 정보를 최신화 유지를 위한 조율 시스템
  2. 클러스터 관리 (Cluster Management)

    • Cluster 추가 / 삭제 시 정보를 서버간 공유
  3. 리더 채택 (Leader Selection)

    • Multi App중 Leader Node를 선정할 로직 생성
    • 주로 복제된 여러 노드 중 연산이 이루어지는 1개의 노드를 택하는데 사용
  4. 락/동기화 서비스 ( Lock and Synchronization Service)

    • Cluster 전체를 대상으로 동기화(Lock)하여 경쟁 상태를 방지하기 위해 사용
    • 연산이 빈번한 경우 경쟁 상태가 될 수 있다
    • 경쟁 상태 여러 프로세스가 동일 자원 접근 시도 데이터 불일치 야기

구성

Server

1개의 Leader, N개의 Follwer, N개의 Observer로 구성된다.
기본적으로 Ensemble 을 구성하기 위해 3개 이상의 홀수 Node가 존재해야한다.

  1. Leader
    • Client가 제출한 모든 요청을 및 데이터 변경을 관리하는 역할
    • 다른 서버들에게 상태 정보 분산
    • 새로운 요청 처리
    • 데이터 동기화
  2. Follwer
    • Client가 제출한 요청을 Leader에게 전달 및 처리
    • Leader Node의 상태를 동기화함
      • Leader에게 문제가 발생하면 Voting을 통해 Leader로 선출됨
    • Follwer가 많아지면 Throuput은 늘어나지만, Failover시 Voting에 시간 소모가 많음
  3. Observer
    • Follwer Node의 일종
      • 차이점 : Voting 권한이 없다.
        • Leader가 될 수 없는 Node이다
    • Data Center의 Bridge, Message Bus의 Link 등의 역할로 활용

Request Processor

Client가 제출한 요청을 Chain으로 연결시켜 Sequential하게 처리하는 프로세스
일반적으로 Single-Thread로 처리함

  • Leader
    • Follower / Client에게 받은 Transaction을 처리해줌
  • Follower / Obserber
    • Client에게 받은 Transaction을 Leader에게 전달

Atomic Broadcast

Zookeeper Server의 데이터 일관성을 ZAB을 이용하여 보장

  • zab : Zookeeper Atomic Broadcast Prodocol
    Pasted image 20230920184247.png
  • 수행 과정
    1. Client에게 요청받은 Leader은 Follower에게 Propose 요청
      • Propose : 수행여부
    2. Propose 받은 Follwer은 해당 Transaction 수행 허용 여부를 Act로 Leader에게 전달
    3. Act를 받은 Leader은 Transaction 처리 명령을 Follwer들에게 Broadcast / Commit

In-Memory DB

Znode를 적재하는 DB

  • Local FS에 In-Memory DB정보를 Replication할 수 있다.
  • Transaction Log가 일정량 이상 되면 Snapshot 후 In-Memory 데이터는 삭제한다.
    • 장애 발생 시 Snapshot을 이용하여 복구

ZNode

Data / 계층을 생성하는 단위
Tree 구조로 구성되어 있다.
Pasted image 20230920184741.png

보유 데이터

  1. ACL( Access Control List )
    1. 접근 권한
  2. ACL Permissions
    1. 행위 권한 ( CRUD 등 )
  3. schemas
    1. 접근 위치 권한 (IP 등)
  4. stat
    1. Node의 정보( 생성 시간, Transaction ID…)

Node 종류

  1. Persistent Node
    1. 영구 노드 ( Non-Falsh)
  2. Ephemeral Node
    1. 휘발성 노드 (Flash )
  3. Sequence Node
    1. 순서가 있는 노드

Watcher

Znode의 변경 사항을 Client / Server에게 알려주는 역할

  • Znode에 Watcher를 등록하여 사용
    • 모니터링 / 알람 역할

Client

zookeeper의 In-Memory DB를 사용하는 Application

  • Client는 Server에게 Heart beat를 전송한다
    • timeout 발생
      • client -> server
        • server/Network Issue, 다른 서버에 연결시도
      • server -> client
        • client/Network Issue, 해당 Session종료

개인적으로 공부한 내용 포스팅 중
잘못된 정보는 지적해주시면 좋겠습니다!

Yarn?

Yet Another Resource Negotiator

  • Hadoop 2.0 에서 시작된 Resource 관리 / 스케줄링 하는 Hadoop 컴포넌트
  • Hadoop 1 에서 사용하던 JobTracker, TasksTracker의 역할 대체
    • 완벽하게 동일한 기능은 아니지만 대다수 대체됨
    • 등록 가능 Node수 4000 -> 클러스터 당 10,000개 이상
    • JobTracker -> ResourceManager
    • TasksTracker -> Node Manager, Container(Slot대체?)

아키텍쳐

Pasted image 20230921185436.png
Resouce Manager은 Master , Node Manager은 Slave로 구성된다.

구성

Resource Manager

  • 클러스터의 자원관리 및 Task 스케줄링이 메인 역할
    1. Client가 Application 실행 요청시 Application Manster을 실행
    2. Node Manager와 통신하여 자원상황 체크
    3. Application Master와 통신하여 필요 자원 관리
  • Hadoop 2.4 부터는 Active - stanby로 구성되어 SPOF 위험 제거

Node Manager

  • Node당 1개 존재
  • Yarn 의 Slave daemon으로서 컨테이너의 자원 관리 역할
  • 사용 중인 자원을 모니터링하고, Resource Manger에게 자원 상황 보고
  • Resource Manager의 요청에 따라 Container 생성

Application Master

  • Application당 1개 존재
  • Resource Manager로부터 Container를 할당 받음
  • Application 실행 상태를 모니터링 및 관리하는 역할

Container

  • 리소스 자원
  • cpu, Disk, Memory 등
      - Application 실행하는 Task들은 Container상에서 실행된다.

개인적으로 공부한 내용 포스팅 중
잘못된 정보는 지적해주시면 좋겠습니다!

'프로그래밍 및 IT > Hadoop' 카테고리의 다른 글

Hadoop  (0) 2023.10.05

Apache에서 오픈소스로 제공하는 분산처리 프레임워크
즉, 대용량 데이터를 여러 서버를 클러스터링 하여 분산처리 하는 것이 목적인 프레임워크
현재 hadoop1.x, hadoop2.x, hadoop3.x 로 발전해왔다
Hadoop-Echosystem으로 여러 Framework와 조합하여 사용한다
Pasted image 20230921152112.png

  • 위 사진에 있다고 필수적으로 모두 사용하는 것은 아니다.
  • 사진 출처

HDFS

Hadoop FileSystem의 약자로 Hadoop의 분산 파일 시스템.

  1. Block단위로 파일을 적재한다
    1. 블록의 수가 너무 많아지면 좋지 않다
      1. Block에 관한 Meta정보를 Namenode에서 관리하여 리소스 낭비가 발생할 수 있다.
    2. 안정성, 다중 처리를 위해 replication을 생성하여 사용한다.
    3. Scale-Out이 용이하다

Mapreduce

Pasted image 20230921151917.png

  • Map과 Reduce 2개의 메소드로 구성된 대용량 데이터 처리 분산 프로그래밍 모델
    • 정형 / 비정형 데이터를 동일한 크기로 나두고, 처리 완료 한 데이터를 병합해주는 역할

Hadoop1.x

Pasted image 20230921152300.png
Hadoop 1.x 버전의 구성은 위와 같다.

Client

NameNode를 통해 정보를 받고, DataNode와 직접 통신

NameNode

Datanode 관리, Resource 관리 등을 하는 Node

  1. MasterNode
    1. SlaveNode의 정보를 저장
    2. HDFS의 Meta data 보관
    3. Client가 데이터 요청 시 위치 정보 전달
    4. 안전성을 위해 Editlog 생성
      1. Editlog : 변경 로그
  2. secondary node
    1. MasterNode가 장애 발생시 대체
    2. MasterNode의 Editslog등을 Pull하여 BackUp/Merge를 수행하여 fsimage 생성
      1. fsimage : File System Image
      2. Editlog의 크기와 fsimage의 생성 시간은 반비례 한다.
      3. fsimage를 MasterNode에 전달하여 동기화
  3. JobTracker
    1. 실행할 task를 관리한다
    2. Job이 끝날 때까지 스케줄링/모니터링을 담당
    3. 클러스터 자원 관리

SlaveNode

데이터가 적재되어있고, 연산 작업을 수행하는 Node

  1. TaskTracker
    1. Task를 수행한다
    2. Map/Reduce Task로 나누어짐
      1. 병렬 처리 작업 단위 : Slot
      2. Map/Reduce slot은 개수가 정해져 있다.
      3. Map/Reduce은 역할이 정해지면 용도 변경이 불가
        1. 작업을 하지 않으면 대기 상태
        2. 클러스터가 100% 활용되지 않을 경우가 존재
  2. DataNode
    1. 데이터를 분산하여 가지고 있따.
    2. 데이터는 Block단위로 적재된다
    3. Fault Recovery를 위해 Duplication을 유지한다
      1. Default : 3
    4. NameNode에게 HeartBeat를 통해 파일위치 및 장애여부 전송

실행 순서 (MapReduce)

  1. client node : M/R 를 수행하기 위해 Job Client를 실행시킴
  2. Job Client : Job을 할당 및 수행하기 위해 JobTracker에게 새로운 Job ID를 수령
  3. Job Client : Jar,Config,Input Split Data을 HDFS에 Job ID디렉토리로 복사
  4. Job Client : JobTracker에게 시작 준비 완료 알림
  5. JobTracker : 실행할 Job 객체 생성
  6. JobTracker : 수행할 Task List 생성을 위해 Job Client가 계산한 Input Split Data를 기반으로 Task 생성
  7. Job,Task Tracker : 상호 Heartbeat 교환
    • task tracker : task 수행 가능여부
    • job tacker : task 가 존재하면 task 반환 후 task tracker가 task를 수행하게 만듦
  8. task tracker : Input Split (Job JAR File)를 HDFS에 복사 후 task runner instance를 생성 후 task수행
  9. task tracker : 각 task를 수행하면서 n초마다 수행 감시

MapReduce의 단일 고장점

  • JobTracker는 모든 MapReduce의 요청을 받는다
    • JobTracker에 문제 발생시 MapReduce는 수행할 수 없다 ( Fail Point )
    • JobTracker가 독점적으로 작업 수령 및 리소스 관리하여 SPOF 위험이 있다.
      • SPOF (Single Point Of Failure) : 1곳에서 장애 발생 시 전 시스템이 중단

클러스터 확장성

종류 최대치
단일 클러스터 4,000
동시 실행 테스크 40,000

리소스 관리

Slot으로 자원 관리하여 Mapper / Reducer의 자원을 효율적으로 사용하지 못 한다P
MapReduce가 아닌 다른 서비스로 인한 자원 영향 파악 불가

HADOOP2.x

Hadoop1 과 차이점

  1. JobTracker, TasksTracker의 역할을 Yarn으로 대체됨
    • 완벽하게 동일한 기능은 아니지만 대다수 대체됨
    • 등록가능 Node수 4000 -> 클러스터 당 10,000개 이상
    • JobTracker -> ResourceManager
    • TasksTracker -> Node Manager, Container(Slot대체?)
  2. Spark, Hive 등 M/R 이외의 분산 처리 모델 지원

Hadoop HA

대표적인 방법으로 2가지가 존재한다

  1. QJM
    1. Journal node를 이용한 HA구성
  2. NFS
    1. Nas를 이용하여 HA를 구성
      Pasted image 20230921185909.png

NFS

Network File System

  • 위 그림은 QJM구성인데, JN부분에 SS로 구성된다면 NFS라고 볼 수 있다.
  • SS ( Shared Storage)
    • NAS ( Network Attached Storeage) 의 묶음
      • Network를 이용한 원격 저장소
    • Namenode의 Journaling 정보를 Nas에 저장 후 동기화 시킴
      • Network, Cpu 등의 문제로 Split Brain이 발생할 수 있다.
        • Split Brain : Context Switch 시 동시에 접근하여 정보 불일치가 발생한는것
          • 이곳에서는 Active Node의 정보가 충돌하여 Node의 정보 불일치

QJM

Quorum Journal Manager

상단의 그림이 QJM이다

  • JN ( Jounal Node)
    • Active NN 과 Standby NN간 동기화를 유지하기 위해 사용되는 Daemon 그룹
      • Daemon : Background 프로그램
    • Active NN 의 Journaling 정보를 지속적으로 기록한다
      • journaling 정보 : 시스템 변경사항 (e.g Edit log)
    • Failover시 Standby NN가 jounaling 정보를 읽었는지 확인 후 Active NN로 성격
    • Quorum을 위해 홀수를 권장
      • 서버 다운을 대비해 JN은 서로 다른 서버에 구성

공통

  • NN ( Name Node)

    • Split Brain 방지를 위해 Active Node와 Standby Node중 Active Node만 동작함
    1. Active Node ( Master Node )
      1. 활동중인 NN
    2. Standby Node ( Slave Node )
      1. Failover을 위해 Active Node와 동기화
        1. Active Node 장애 발생 시 Active로 승격
      2. NFS 의 SS, QJM의 JN를 이용하여 동기화
      3. Standby Node가 존재하면 SecondName / Checkpoin / Backup Node 불필요
        1. 위 3개와 동시에 동작 시 Error 발생
    3. Observer Node ( Hadoop 3.x 이후 추가)
      1. Hadoop Cluster의 규모가 커지면서 Active Node가 관리하는 Object가 증가함
        1. OverHead가 증가하여 Active Node의 부하가 증가
      2. Active Node의 과부하 방지를 위해 Active Node의 Read역할을 대신 해준다
        1. Traffic 분산
  • DN ( Data Node )

    • Data를 분산 저장하는 Node
    • Darta는 기본값으로 3개의 replication을 가지고 있다
  • ZK( Zookeeper )

    • Coordinator로써 Server의 Leader선정시 사용
  • ZKFC( Zookeeper Failover Controller )

    • ZK - NN 사이에서 모니터링 , 세션관리, 장애 복구를 수행하는 프로세스
      • Health Monitoring
        • NN과 ping 즉 heartbeat를 주고 받으면서 상태 확인 ( Timeout 기반)
        • NN의 장애 (충돌, 정지, …) 발생시 NN비정상 표기
      • Session Management
        • NN 정상
          • Session이 열린 상태를 유지한다
            • Active NN가 임시 Lock ZNode를 사용
        • NN 비정상
          • Session 종료 후 ZK에 알람
        • NN 종료
          • 자동으로 할당한 임시 Lock ZNode를 삭제
      • zookeeper-based Election
        • ZK기반으로 Active NN 선정
        • Active NN 장애 발생 시 Standby NN는 Lock Node를 선점 시도
          • 1+N개의 Standby NN가 존재하면 최초 선점함 NN가 Active로 승격
      • Fencing
        • Standby NN가 Active NN로 승격하는 과정에서 기존 Active NN가 죽지 않아 2개의 Active NN가 되는 걸 방지하기 위해 기존 Active NN를 죽이는 기법
        • Active NN를 Standby NN로 변경하거나 Kill한다
    • NN과 같은 Host에 구성된 ZK와 상호장용하는 Controller

개인적으로 공부한 내용 포스팅 중
잘못된 정보는 지적해주시면 좋겠습니다!

'프로그래밍 및 IT > Hadoop' 카테고리의 다른 글

Yarn  (0) 2023.10.05

데이터 이전 후 설명 없는 NullPointerException

 ERROR TaskSetManager: Task 0 in stage 5.0 failed 4 times; aborting job
org.apache.spark.SparkException: Job aborted due to stage failure: Task 0 in stage 5.0 failed 4 times, most recent failure: Lost task 0.3 in stage 5.0  : java.lang.NullPointerException
    at org.apache.spark.sql.execution.datasources.orc.OrcColumnVector.getUTF8String(OrcColumnVector.java:167)
    ...

데이터 이전을 잘 하고 나머지 집계도 잘 동작하는지 확인하기 위해 검증하는 도중 원인 설명이 제대로 되지 않은 문제가 발생했다.

원인

이전 이전의 Table에 필요한 columns을 추가하였고, 생성문은 관련된 columns끼리 묶어 관리하기 위해 순서를 변경함

그로 인하여 기존 테이블 스키마 순서와 이전할 테이블의 순서가 다르기 때문에 문제가 발생함.

간단 설명

  1. 아래와 같은 테이블이 존재했다 가정하고 시작해보자

    id passwd name
    id1 passwd1 nane1
    id2 passwd2 nane2
    id3 passwd3 nane3
  2. email칼럼을 추가하기위해 데이터를 추가하였다.

    id passwd name email
    id1 passwd1 nane1 email1
    id2 passwd2 nane2 email2
    id3 passwd3 nane3 email3
  3. 이전한 테이블은 id,passwd,email,name 순으로 테이블 스키마를 정의했다.

  4. create external table if not exists db명.tb명 ( id string , passwd string , email string , name string ) ;

  5. 복제할때 기존 테이블의 스키마 순서인 id,passwd,name,email 가아닌 id,passwd,email,name 로 스키마 순서가 바뀌어 데어터 순서가 뒤섞여 복제가 되었다.

    id passwd email name
    id1 passwd1 nane1 email1
    id2 passwd2 nane2 email2
    id3 passwd3 nane3 email3

해결책

1번 해결책

생성문을 기존 칼럼 순서와 동일하게 만든다.

create external table if not exists db명.tb명 (
      id      string
    , passwd  string
    , name    string
    , email   string
)
;
  • 위에 설명한 원인을 예시로 보면 위와 같이 기존 테이블 순서에 맞게 변경한 후 이관시킨다
  • 하지만 이 방법은 columns끼리 묶으려고 순서를 변경하였기에 썩 좋지 않은 방법이라고 생각한다.

2번 해결책 ( 실패 )

ALTER TABLE test_change CHANGE [ col_name ] [col_new_name] [type] [location] 을 이용하여 순서변경

alter table db명.tb명 change id     id      string first         ;
alter table db명.tb명 change passwd passwd  string after  id     ;
alter table db명.tb명 change name   name    string after  passwd ;
alter table db명.tb명 change email  email   string after  name   ;
  • 실 구동은 해보지 않음 hive cwiki

  • 아래 테이블의 차이처럼 metadata 까지 변경 되는것으로 보이기 때문에 기각

    id passwd email name
    id1 passwd1 nane1 email1
    id2 passwd2 nane2 email2
    id3 passwd3 nane3 email3
    id passwd name email
    id1 passwd1 email1 nane1
    id2 passwd2 email2 nane2
    id3 passwd3 email3 nane3

3번 해결책 ( 성공 )

select a.CD_ID, a.COLUMN_NAME, a.INTEGER_IDX
from hive.COLUMNS_V2 a
inner join hive.SDS b
    on  b.CD_ID = a.CD_ID
inner join hive.TBLS c
    on  c.SD_ID = b.SD_ID
    and c.TBL_NAME = 'table_name'
order by INTEGER_IDX
;
  • 출력 예시

    CD_ID COLUMN_NAME INTEGER_IDX
    504 member_id 0
    504 char_id 1
    504 first_time 2
    504 last_time 3
    504 reg_time 4
  • 위와 같이 metastore 정보를 확인해보면 COLUMN_NAME,integer_idx을 확인할 수 있다.

  • 해당 COLUMN_NAME과 INTEGER_IDX의 값과 순서를 기존 테이블과 동일하게 만들어주면된다.

  • 따로 외래키등이 걸려있지 않아서 해당 CD_ID의 값을 insert overwrite로 해결하였다.

추정되는 원인

기존에 hive.metastore.schema.verification=false로 처리가 되어 있어 schema 검증을 제대로 안 되서 그런 것으로 추정됨

hive --orcfiledump /File_Path 이 명령어를 이용하여 orc 파일의 schema를 확인해보니, 아래와 같다.

  1. hive.metastore.schema.verification=true

    Structure for /File_Path
    File Version: 0.12 with HIVE_8732
    Rows: 1151
    Compression: SNAPPY
    Compression size: 262144
    Type: struct<member_id:string,char_id:string,first_time:timestamp,last_time:timestamp,reg_time:timestamp>
    
    Stripe Statistics:
    Stripe 1:
        ...
    
    File Statistics:
    ...
    
    Stripes:
    ...
  2. hive.metastore.schema.verification=false

    Structure for /File_Path
    File Version: 0.12 with HIVE_13083
    Rows: 1095
    Compression: SNAPPY
    Compression size: 262144
    Type: struct<_col0:string,_col1:string,_col2:timestamp,_col3:timestamp,_col6:timestamp>
    
    Stripe Statistics:
    Stripe 1:
        ...
    
    File Statistics:
    ...
    
    Stripes:
    ...

위 결과를 보면 hive.metastore.schema.verification=true를 해야 orc의 schema값이 Hive의 스키마로 잘 생성된다.

  1. true

    • Type: struct<member_id:string,char_id:string,first_time:timestamp,last_time:timestamp,reg_time:timestamp>
  2. false

    • Type: struct<_col0:string,_col1:string,_col2:timestamp,_col3:timestamp,_col6:timestamp>

데이터 이전 전의 테이블이 false로 되어있던 것 이기 때문에 테스트는 하지 못 하였으나, 겪은 문제처럼 칼럼 순서가 뒤바뀐 이유는 이것으로 추정된다.

이전 사유

HDP 라이센스 문제로 Hadoop-EchoSystem 재구축함에 따라 HDFS, Hive의 버전을 변경하게 됬다

  • HDFS 2.7.3 -> 3.1.1
  • Hive 1.6.3 -> 3.1.2

이전 방법

데이터 복사

# hdfs dfs -cp -f -p src dist
hdfs dfs -cp -f -p hdfs://기존HDFS 주소/기존 테이블 경로/*  hdfs://이전될 HDFS 주소/기존 테이블 경로  
  • (hdfs://이전될 HDFS 주소) 은 명령어 실행위치가 loacal이면 생략해도 된다.
  • option ( 필요 없다면 생략 가능 )
    • f : 덮어쓰기
    • p : 파일정보 그대로 가져가기 e.g 생성일자, 생성 user, group.. 등

복사(전송) 확인

# hdfs dfs -ls path
hdfs dfs -ls /apps/hive/dbName/tbName
drwxr-xr-x   - hive hadoop          0 2022-09-15 19:38 /apps/hive/dbName/tbName
.....
  • 위와 같이 기존과 동일한 hive partition 구조로 디렉토리 및 파일이 잘 전송됬으면 된다.
  • (hdfs://이전될 HDFS 주소) 은 명령어 실행위치가 loacal이면 생략해도 된다.

테이블 인식

msck repair table bd명.tb명;
  • 위와 같이 테이블 복구(msck repair)를 해주면 끝이다.
    • hdfs에는 옮겨졌지만, metastore은 인식하고 있지 않으니 msck repair을 해줘야한다
    • 궁금하다면 msck를 하기전에 조회를 해보고, msck를 한 후 조회를 해보면 msck를 한 기점으로 조회가 되는 것을 확인할 수 있을 것 이다.

결론

우연치 않은 기회로 Hive Records 이전 작업을 수행했다.

처음에는 cp 명령어로 간단하게 될까 했는데 진짜 되서 당황스러웠다,

그래도 막히는 부분이 있어서 여러 문제에 봉착할 줄 알았지만, 기존 테이블과 동일한 조건으로 생성한 후 진행해서 그런지 첫 시도에 해결을 했고 시간을 많이 안 잡아먹어서 다행이다.

이제 저것을 기반으로 shell script만 만들고 성공하면 운영 서버 데이터 이전할 때 편안하게 사용해야겠다.

작성 후 작업중 추가로 발생한 에러

데이터 이전 후 추가로 발생한 에러

'프로그래밍 및 IT > Hive' 카테고리의 다른 글

Hive  (0) 2023.10.24

Version

  1. Spark : 1.6.3
  2. hdfs : 2.7.3
  3. Hive : 1.2.1

기분좋게 휴가를 다녀왔더니 집계 메일이 와있어 호다닥 이슈를 확인해 봤다.

실패한 Spark 집계 및 상당히 느려진 Spark 집계... 당혹스러웠다.

Spark UI를 확인하면 아래와 같다.

image

분명 집계 개선을 하여 3분대로 낮춰놨는데, 당혹스럽게 위 사진과 같이 불필요한 wait 시간이 29분이나 되는 것을 확인할 수있다. total Uptime과 비교하면 실직적으로 집계를 수행한 시간은 1분 남짓인데, 기다린 시간이 29분인 것을 보니 상당히 큰 이슈였다.

그래서 Hadoop Application 에서 로그를 확인해 보니 아래와 같은 문제가 발생하였다.

ERROR Hive: org.apache.thrift.transport.TTransportException: java.net.SocketTimeoutException: Read timed out
    at org.apache.thrift.transport.TIOStreamTransport.read(TIOStreamTransport.java:129)
    at org.apache.thrift.transport.TTransport.readAll(TTransport.java:86)
    ...
Caused by: java.net.SocketTimeoutException: Read timed out
    at java.net.SocketInputStream.socketRead0(Native Method)
    ... 134 more

내부망으로 DataNote 통신을 하는데 TimeOut인 것은 뭔가 문제가 있어보였다.

다른 문제점이 무엇이 있는지 확인할 겸 Ambari를 확인해보니, HiveMetastore에 Alert가 발생하였다 .

        Metastore on ambariserver.coresight.com failed (Traceback (most recent call last):
  File "/var/lib/ambari-agent/cache/common-services/HIVE/0.12.0.2.0/package/alerts/alert_hive_metastore.py", line 203, in execute
    timeout_kill_strategy=TerminateStrategy.KILL_PROCESS_TREE,
  File "/usr/lib/python2.6/site-packages/resource_management/core/base.py", line 166, in __init__
    self.env.run()
  File "/usr/lib/python2.6/site-packages/resource_management/core/environment.py", line 160, in run
    self.run_action(resource, action)
  File "/usr/lib/python2.6/site-packages/resource_management/core/environment.py", line 124, in run_action
    provider_action()
  File "/usr/lib/python2.6/site-packages/resource_management/core/providers/system.py", line 262, in action_run
    tries=self.resource.tries, try_sleep=self.resource.try_sleep)
  File "/usr/lib/python2.6/site-packages/resource_management/core/shell.py", line 72, in inner
    result = function(command, **kwargs)
  File "/usr/lib/python2.6/site-packages/resource_management/core/shell.py", line 102, in checked_call
    tries=tries, try_sleep=try_sleep, timeout_kill_strategy=timeout_kill_strategy)
  File "/usr/lib/python2.6/site-packages/resource_management/core/shell.py", line 150, in _call_wrapper
    result = _call(command, **kwargs_copy)
  File "/usr/lib/python2.6/site-packages/resource_management/core/shell.py", line 297, in _call
    raise ExecuteTimeoutException(err_msg)

내용을 보아하니 대충 Metatore에 문제가 발생하였다는 것을 볼 수 있다.

그럼으로 해당 문제를 확인하기 위해 (Hortnworks기준) /var/log/hive/hivemetastore.log 를 확인해 보니 아래와 같은 엄청난 것을 볼 수 있었다.

image

위와 같은 충격적인 Log를 확인하고, Error문구를 확인하니 아래와 같았다.

com.mysql.jdbc.PacketTooBigException: Packet for query is too large (1048964 > 1048576). You can change this value on the server by setting the max_allowed_packet' variable.
        at com.mysql.jdbc.MysqlIO.send(MysqlIO.java:3279)
        at com.mysql.jdbc.MysqlIO.sendCommand(MysqlIO.java:1971)
        ...

에러 문구를 보니 설정한 max_allowed_packet 보다 많은 양의 packet보내 문제가 발생하였다는 것이였다.

필자는 mysql 을 5.1버전을 사용하고 있는데, Default값이 1MB인지, Hortenworks의 Default값인지 정확하게 확인은 하지 않았지만, 상대적으로 낮은 사이즈로 설정되어있었다. (5.7 버전의 Default값은 4MB였다.)

이것을 해결 하는 방법은 여러가지가 있겠지만, 필자가 생각하는 방법은 2가지가 있다.

  1. 더 작은 패킷을 보낸다

    • 사실상 원하는 해결책이 아님
  2. max_allowed_pachet을 늘린다.

    1. 당장 바꾸고 싶다면 아래와 같이 하면 된다

       SET GLOBAL max_allowed_packet = 33554432;        
       FLUSH PRIVILEGES;        
       show variables where Variable_name = 'max_allowed_packet';
    2. /etc/my.cnf 에 max_allowed_pachet 추가해줌

       [mysqld]
       datadir=/var/lib/mysql
       socket=/var/lib/mysql/mysql.sock
       user=mysql
       # Disabling symbolic-links is recommended to prevent assorted security risks
       symbolic-links=0
       max_allowed_packet=32M
      • 굳이 32MB일 필요는 없다
    3. mysql을 재시작 해주면된다.

여러가지 문제를 경험해야 많은 것을 배울 수 있는 것 같다.

만약 설정된 max_allowed_packet가 1MB가 아니여서 위와 같은 Error가 발생하지 않았다면,
회사에서 5년치 데이터를 한번에 읽어 처리하여 Pachet량이 1mb를 넘기지 않았다면 필자는 해당 문제를 경험하지 않아 고민을 하지 않았을 것 같다.

물론 문제가 발생하여 짜증은 났지만, 해결한 현재는 좋은 경험이였다고 생각한다.

+ Recent posts