LabHub
배우기 러닝패스 코스

데이터 파이프라인 · 실행 원장과 원자적 커밋 · 실습

새벽 3시에 죽은 정산 작업 — 원장과 원자적 교체

LabHub 에서 이어서 보기

목표

도중에 죽어도 안전한 실행기 runner.py 를 만든다. 산출물을 임시 이름으로 쓰고 바꿔 달아 반쯤 쓰인 파일이 남지 않게 하고, 실행 한 번을 원장에 한 줄로 남기고, 죽은 조각부터 재개하고, 같은 실행을 두 번 커밋해도 숫자가 늘지 않게 만든다.

왜 중요한가

파이프라인은 반드시 도중에 죽는다. 문제는 죽는다는 사실이 아니라, 죽었을 때 무엇이 남느냐다. 목적지 파일에 직접 쓰고 있었다면 반쯤 쓰인 파일이 남고, 그 파일은 크기도 이름도 멀쩡해서 다음 단계가 그대로 읽어 간다.
다시 돌리는 것도 위험하다. 앞 실행이 어디까지 갔는지 기록이 없으면 처음부터 다시 도는 수밖에 없고, 마지막에 장부로 덧붙이는 자리에서 같은 금액이 두 번 더해진다. 이것이 "다시 돌렸는데 왜 두 배가 됐나" 의 정체다.
이 실습이 만드는 장치는 셋이다. 첫째는 원자적 교체다. 같은 디렉터리에 임시 이름으로 다 쓴 뒤 os.replace 로 바꿔 단다. 둘째는 실행 원장이다. 실행마다 한 줄을 덧붙이고, 실패했다면 어느 조각에서 죽었는지를 적는다. 셋째는 재개다. 끝난 조각의 산출물 자체를 표식으로 삼아 건너뛴다.
이 코스의 dp-idempotent 실습은 데이터베이스 쪽 멱등성을 다룹니다 — 같은 행을 두 번 넣어도 한 행이 되게 만드는 일입니다. 여기는 그 앞자리입니다. 프로세스가 죽은 자리에서 파일 시스템에 무엇이 남는가, 남은 것을 보고 어디부터 다시 시작할 것인가를 다룹니다.
채점기는 여러분이 적어 낸 문구를 믿지 않는다. 임시 디렉터리에 채점기가 만든 입력 조각을 차려 놓고 여러분의 실행기를 실제로 돌린다. 일부러 죽인 뒤 목적지 파일이 그대로인지, 임시 파일이 목적지 옆에 남았는지, 원장에 실패한 조각 이름이 적혔는지까지 본다. 조각 수와 금액은 실행마다 바뀐다.

단계

1. /root/runx/gen_shards.py 를 만들어 실행해 /root/runx/work/in 아래 입력 조각을 만드세요.
2. /root/runx/runner.pyscan 을 만들어 조각 목록과 건수와 합계를 내게 하세요.
3. part 를 더해 조각 하나를 처리하고 산출물을 임시 이름으로 썼다가 바꿔 달게 하세요. --crash=write 로 바꿔 달기 직전에 죽는 길도 만듭니다.
4. run 을 더해 조각 전체를 처리하고 합친 산출물을 만들게 하세요.
5. 실행마다 원장 한 줄을 남기고 ledger 로 요약을 내게 하세요.
6. --crash-shard 로 가운데 조각에서 죽게 하고, 원장에 실패한 조각이 남고 합친 산출물은 건드려지지 않는지 확인하세요.
7. --resume 을 더해 끝난 조각을 건너뛰고 죽은 자리부터 이어 가게 하세요.
8. commit 을 더해 하루치 장부 /root/runx/work/out/daily.jsonl 에 같은 실행이 두 번 붙지 않게 하세요.

참고

단계 8개

  1. 상류가 떨어뜨린 조각 만들기
  2. 무엇이 들어왔는지 먼저 센다
  3. 목적지에 직접 쓰지 않는다
  4. 실행 하나로 묶기
  5. 실행 한 번을 한 줄로 남기기
  6. 가운데 조각에서 죽여 보기
  7. 죽은 자리부터 이어 가기
  8. 두 번 붙지 않게 하기