TT Lab
시작하기
배우기 러닝패스 코스

Apache Hadoop — HDFS 와 YARN 을 한 파드에 세우고 운영한다

1바이트 파일이 30MB 쿼터에 막히는 이유를 재현한다

TT Lab 에서 이어서 보기

목표

디렉터리에 이름 쿼터와 공간 쿼터를 걸고, 이름 쿼터가 디렉터리 자신까지 센다는 것과 공간 쿼터가 블록 크기 × 복제 계수만큼 미리 예약한다는 것을 거절 메시지로 확인한다. 블록 크기를 줄여 같은 파일을 들여보내고, 쿼터가 옮기기(mv)까지 막는다는 것도 본다.

왜 중요한가

여러 팀이 한 HDFS 를 나눠 쓰면 한 팀의 실수(무한히 파일을 만드는 잡, 작은 파일 수백만 개)가 NameNode 의 힙과 디스크를 모두의 것에서 빼앗는다. 쿼터는 그 피해를 디렉터리 하나에 가두는 장치다. 이름 쿼터는 파일과 디렉터리의 개수를, 공간 쿼터는 복제본까지 포함한 바이트를 제한한다. 공간 쿼터에는 함정이 하나 있다. 파일을 쓰기 시작할 때 NameNode 는 아직 몇 바이트를 쓸지 모르므로 블록 하나를 통째로(블록 크기 × 복제 계수) 예약한다. 그래서 남은 쿼터가 128MB 보다 작으면 1바이트 파일도 들어가지 못한다. 쓰기가 끝나면 실제 크기로 정산되지만, 시작조차 못 하면 소용없다. 운영에서 "쿼터가 남았는데 왜 못 쓰냐" 는 문의의 대부분이 이것이다. 쿼터는 새 이름이 생기는 모든 일에 걸린다. 다른 디렉터리에서 옮겨 오는 것도 그 디렉터리 입장에서는 새 이름이다.

단계

  1. HDFS /quota/team-a 를 만들고 이름 쿼터 10 을 거세요(hdfs dfsadmin -setQuota).
  2. 작은 로컬 파일을 하나씩 team-a 에 올려 거절될 때까지 채우고, 거절된 put 의 오류 출력을 /root/hdp/quota/quota_err.txt 에 저장하세요.
  3. /quota/team-b 를 만들고 공간 쿼터 30MB 를 거세요(hdfs dfsadmin -setSpaceQuota 30m).
  4. 1바이트짜리 로컬 파일 /root/hdp/quota/one.txt 를 만들어 /quota/team-b/one.txt 로 올려 보고, 오류 출력을 /root/hdp/quota/space_err.txt 에 저장하세요.
  5. 같은 파일을 블록 크기 1MiB(-D dfs.blocksize=1048576)로 /quota/team-b/one-1m.txt 에 올리세요.
  6. hdfs dfs -count -q -v /quota/team-a /quota/team-b 출력을 /root/hdp/quota/count.txt 에 저장하세요.
  7. /quota/staging 을 만들어 파일 하나(/quota/staging/f.txt)를 올린 뒤, 그것을 team-a 로 -mv 해 보고 오류 출력을 /root/hdp/quota/mv_err.txt 에 저장하세요.
  8. /root/hdp/quota/report.md 에 ## 이름 쿼터 ## 공간 쿼터 ## 쿼터가 막는 것 세 절을 쓰세요. 첫 절에 team-a 에 실제로 들어간 파일 수를, 둘째 절에 예약하려던 바이트 수(134217728)를 넣으세요.

참고

이름 쿼터 걸기

HDFS /quota/team-a 를 만들고 hdfs dfsadmin -setQuota 10 /quota/team-a 로 이름 쿼터 10 을 거세요.

이름 쿼터는 그 디렉터리 아래(자신 포함)의 파일과 디렉터리 개수 상한입니다. 걸린 값은 hdfs dfs -count -q 의 첫 칸에서 봅니다.

10 인데 몇 개가 들어가나

작은 로컬 파일을 여러 개 만들어 하나씩 hdfs dfs -put 으로 /quota/team-a/ 에 올리다가, 거절된 put 의 오류 출력(표준 오류)을 /root/hdp/quota/quota_err.txt 에 저장하세요.

디렉터리 자신도 이름 하나로 셉니다. 그래서 파일은 쿼터보다 하나 적게 들어갑니다. 거절 메시지에 쿼터와 '넣으려던 뒤의 개수' 가 함께 찍힙니다.

공간 쿼터 걸기

HDFS /quota/team-b 를 만들고 hdfs dfsadmin -setSpaceQuota 30m /quota/team-b 로 공간 쿼터 30MB 를 거세요.

30m 은 30 × 1024 × 1024 바이트입니다. 공간 쿼터는 복제본까지 센 실제 디스크 사용량의 상한입니다.

1바이트가 막힌다

1바이트짜리 로컬 파일 /root/hdp/quota/one.txt 를 만들고(printf x > /root/hdp/quota/one.txt) hdfs dfs -put 으로 /quota/team-b/one.txt 에 올려 보세요. 오류 출력을 /root/hdp/quota/space_err.txt 에 저장하세요.

쓰기를 시작하는 순간 NameNode 는 블록 하나(블록 크기 × 복제 계수)를 예약합니다. 기본 블록 크기 128MB 는 30MB 쿼터보다 큽니다. 메시지의 두 숫자 — 쿼터와 필요했던 공간 — 를 견줘 보세요.

블록을 작게 잡으면 들어간다

같은 /root/hdp/quota/one.txt 를 hdfs dfs -D dfs.blocksize=1048576 -put 으로 /quota/team-b/one-1m.txt 에 올리세요.

블록 크기가 1MiB 면 예약도 1MiB 입니다. 쓰기가 끝나면 사용량은 실제 크기(1바이트 × 복제 계수)로 정산됩니다. -count -q 의 REM_SPACE_QUOTA 가 얼마나 줄었는지 보세요.

count -q 로 두 쿼터 읽기

hdfs dfs -count -q -v /quota/team-a /quota/team-b 출력을 /root/hdp/quota/count.txt 에 저장하세요.

쿼터가 없는 칸은 none/inf 로 찍힙니다. team-a 는 REM_QUOTA 가 0 이고, team-b 는 공간이 거의 그대로 남아 있습니다 — 거절은 '남은 양' 이 아니라 '예약할 양' 때문이었습니다.

옮기기도 쿼터에 걸린다

HDFS /quota/staging 을 만들어 파일 하나를 /quota/staging/f.txt 로 올린 뒤, hdfs dfs -mv /quota/staging/f.txt /quota/team-a/ 를 해 보고 오류 출력을 /root/hdp/quota/mv_err.txt 에 저장하세요.

옮기기는 바이트를 움직이지 않지만 team-a 입장에서는 이름이 하나 늘어납니다. 그래서 이름 쿼터가 거절하고, 파일은 staging 에 그대로 남습니다.

쿼터 문의에 답할 수 있게

/root/hdp/quota/report.md 에 ## 이름 쿼터 ## 공간 쿼터 ## 쿼터가 막는 것 세 절을 쓰세요. 첫 절에 team-a 에 실제로 들어간 파일 수를, 둘째 절에 4단계에서 예약하려던 바이트 수를 숫자로 넣으세요.

'쿼터 10 인데 왜 9개만 들어가요?', '30MB 가 남았는데 왜 1바이트도 못 써요?' 라는 문의에 답한다고 생각하고 쓰세요.