LabHub
배우기 러닝패스 코스

FDE総合演習:倉庫に同じ注文が3回届いた

1.5.0 は受付済みと表示したが、倉庫に注文はなかった

LabHub 에서 이어서 보기

한국어 원문으로 표시합니다.

목표

releases/<판> 과 current 심링크로 배포하고, 헬스체크와 스모크 시험을 거쳐 실패하면 직전 판으로 되돌려 기록하는 스크립트를 만든다. 보존 정리에서 current 와 직전 판을 지킨다.

왜 중요한가

헬스체크는 프로세스가 살아 있는지를, 스모크는 업무 한 건이 끝까지 되는지를 묻는다. 고객사의 지난 배포는 앞의 질문만 하고 끝나 밤새 주문을 잃었다. 판을 디렉터리로 나누고 심링크 하나로 전환하면 되돌림도 같은 동작 하나가 된다. 다만 전환하는 순간 current 가 사라지거나, 옛 프로세스가 대신 초록불을 켜거나, 정리 스크립트가 돌아갈 판을 지우면 구조가 있어도 사고가 난다. 채점기는 매번 다른 판 번호로 정상·스모크에서만 깨지는·뜨자마자 죽는·늦게 뜨는 빌드를 만들어 여러분의 스크립트를 실행하고, 로그 문구가 아니라 실제로 응답하는 판과 심링크를 다시 잰다.

예상 60분이다. 기본 세션이 끝나기 전에 +시간으로 연장하자(최대 180분). 세션이 끝나면 /root 의 파일은 사라지니 스크립트는 따로 보관한다.

단계

  1. 빌드 orderapp-1.4.0.tar.gz 를 /root/site/releases/1.4.0 에 풀고, /root/site/current 심링크가 그 디렉터리를 가리키게 한다.
  2. /root/release/switch.sh ROOT 판 을 만든다. 없는 판은 거부하고, current 가 사라지는 순간 없이 한 번에 전환한다.
  3. /root/release/deploy.sh ROOT 빌드 PORT 를 만든다. 풀기·전환·옛 프로세스 교체·헬스체크(version 확인)·스모크 주문·deploy.log 기록까지 정상 빌드로 통과시킨다.
  4. deploy.sh 가 스모크에 실패하면 current 를 직전 판으로 되돌리고 그 판을 다시 띄운 뒤 rolled_back·reason smoke 를 기록하고 종료 코드 2 로 끝나게 한다.
  5. deploy.sh 의 헬스체크가 뜨자마자 죽는 판은 health 로 되돌리고, 2.5초 늦게 뜨는 정상 판은 기다려서 배포하게 한다. 대기 상한은 10초다.
  6. /root/release/prune.sh ROOT KEEP 을 만든다. mtime 최신 KEEP 개를 남기되 current 와 직전 판은 지울 목록에서 뺀다.
  7. 네 번 배포(마지막은 스모크 실패)와 보존 1 정리를 이어서 해도 기록·남은 판·응답하는 판이 맞는지 확인한다.
  8. 고객의 1.5.0 을 deploy.sh 로 /root/site(포트 8480)에 배포해 결과를 보고, /root/release/incident.json 에 사건을 기록한다.

참고

첫 판을 손으로 풀고 current 걸기

빌드 1.4.0 을 /root/site/releases/1.4.0 에 풀고 /root/site/current 심링크가 그곳을 가리키게 하세요.

tar 의 -C 로 풀 자리를 정합니다. current 는 디렉터리 복사가 아니라 ln -s 로 만든 링크여야 합니다. 상대 경로 링크(releases/판)는 배포 루트를 통째로 옮겨도 깨지지 않습니다.

current 를 한 번에 바꾸는 전환 스크립트

/root/release/switch.sh ROOT 판 을 만드세요. 없는 판은 0 이 아닌 코드로 거부하고 current 는 사라지는 순간 없이 바뀌어야 합니다.

rename(2) 는 기존 이름을 원자적으로 교체합니다. 같은 디렉터리에 임시 링크를 만들고 current 위로 옮기세요. mv 에는 대상이 디렉터리를 가리켜도 그 안으로 넣지 않게 하는 옵션이 있습니다. ln 을 쓴다면 -n 을 빠뜨리지 마세요.

풀고 바꾸고 띄우고 스모크까지

/root/release/deploy.sh ROOT 빌드 PORT 를 만들어 정상 빌드를 배포하고 deploy.log 에 deployed 한 줄을 남기세요.

판은 tar 안의 VERSION 에서 읽습니다. 옛 프로세스는 shared/app.pid 로 내리고, 새 앱은 nohup 과 출력 리디렉션으로 백그라운드에 띄웁니다. 헬스체크 응답의 version 이 새 판인지, 스모크 주문(SMOKE- 접두어)이 GET 으로 되읽히는지 봅니다. 기록은 jq -cn 으로 만들면 따옴표 실수가 없습니다.

스모크가 깨지면 직전 판으로 되돌리기

/root/release/deploy.sh 가 스모크 실패 시 직전 판으로 전환·재기동하고 rolled_back(reason smoke)을 기록한 뒤 종료 코드 2 로 끝나게 하세요.

전환 전에 current 가 가리키던 판을 previous 로 기억해 두어야 되돌릴 곳을 압니다. 되돌림도 switch.sh 로 합니다. 실패한 releases/판 은 조사용으로 남깁니다.

죽은 판은 빨리, 늦은 판은 기다려서

/root/release/deploy.sh 의 헬스체크가 최대 10초를 기다리되 프로세스가 죽으면 곧바로 health 로 되돌리게 하세요.

한 번 실패했다고 포기하면 늦게 뜨는 정상 판을 되돌립니다. 반대로 이미 죽은 프로세스를 10초 기다릴 이유는 없습니다. kill -0 PID 는 신호를 보내지 않고 프로세스가 있는지만 확인합니다.

정리하다 돌아갈 판을 지우지 않기

/root/release/prune.sh ROOT KEEP 을 만드세요. mtime 최신 KEEP 개 외에는 지우되 current 와 직전 판은 남깁니다.

되돌림 뒤에는 current 가 최신이 아닙니다. 직전 판은 deploy.log 에서 result 가 deployed 이고 version 이 current 인 마지막 줄의 previous 입니다. ls -t 는 수정 시각 최신순으로 나열합니다.

네 번 배포하고 정리해도 맞는 기록

/root/release/deploy.sh/root/release/prune.sh 가 배포 네 번(마지막은 스모크 실패)과 보존 1 정리를 이어서 해도 기록과 실제 상태가 맞게 하세요.

되돌린 배포의 previous 는 되돌아간 판입니다. 그 뒤 정리하면 최신 1개(실패한 판)와 current·직전 판이 남아야 합니다. 임시 배포 루트에서 직접 이어서 돌려 보세요.

고객의 1.5.0 을 배포하고 사건 기록 남기기

deploy.sh 로 1.5.0 을 /root/site(포트 8480)에 배포하고, 결과를 /root/release/incident.json 에 failed_version·restored_version·reason·deploy_log_line·health_passed 로 적으세요.

deploy_log_line 은 /root/site/deploy.log 에서 되돌림 기록이 몇 번째 줄인지(1부터)입니다. health_passed 는 이 판이 헬스체크를 통과했는지를 적습니다 — app.log 와 기록의 reason 으로 판단하세요. 채점기는 incident.json 을 deploy.log·current·빌드 원본과 대조합니다.