«zero downtime» 설정 관련 도움

“다운타임 제로” 구성 방식을 이해하려고 노력하고 있습니다. 현재 저는 서로 다른 커뮤니티를 위해 Discourse 인스턴스를 두 개 운영하고 있습니다. 두 인스턴스 모두 data/web 2 컨테이너 구성을 사용하고 있습니다. 호스트 레벨에서 SSL 종료를 처리하고, 소켓 연결을 컨테이너의 Nginx로 전달하는 Nginx가 설정되어 있습니다.

관심 있는 두 가지 주제를 발견했습니다:

이 프로세스를 이해하려고 하고 있습니다. 이 작업을 수행하기 위해 어느 정도 사전 지식이 필요한 것 같습니다. 누군가 여기서 도움을 줄 수 있다면 정말 좋겠습니다.

가장 먼저 이해하고 싶은 것은 data 컨테이너가 업그레이드되어야 하는 시기를 어떻게 알 수 있는가입니다. web 컨테이너만 재빌드해서는 안 되는 경우가 있는 것 같습니다. 이런 경우가 언제인지 확실히 어떻게 알 수 있을까요? 업그레이드 옵션이 관리 UI 패널에서 회색으로 표시되는 모든 경우, 그리고 테마 및 플러그인에 대한 잠재적인 커스텀 작업이 포함되는 경우를 말씀하시는 건가요? 데이터베이스 스키마 마이그레이션을 살펴봄으로써 확실히 알 수 있을까요? 확실히 알기 위해 스테이징 환경을 구축하고 직접 시도해 봐야 할까요?

다음으로 알고 싶은 것은 다운타임 제로 업그레이드를 어떻게 실행하는가입니다. 두 링크를 읽어본 결과, 결국 data 컨테이너와 web 컨테이너를 모두 재빌드하게 되는 것 같습니다. 이 부분을 이해하기 어렵습니다. 최종적으로 다운타임 제로를 달성하려면 별도의 data/web 컨테이너가 필요할까요?

어떤 지침이든 환영합니다! 많은 시간을 들여 작동하는 것처럼 보이는 방법을 알아낼 수도 있겠지만, 거인의 어깨 위에 올라서서 (:)) 가능하면 하드한 방식으로(프로덕션에서) 엣지 케이스를 발견하지 않고 해결하는 편이 낫다고 생각합니다.

제 특정 설정에 대해 더 많은 정보가 필요하시다면, 명확히 설명해 달라고 말씀해 주세요. 직접 답변을 드리며 이 게시물을 업데이트하겠습니다.

감사합니다.

“배포 후 마이그레이션”에 대해 자세히 알지는 못하지만, 제가 여기서(메타) 읽은 기억에 따르면, 이를 구현하는 방법 중 하나는 컨테이너 3개(데이터 1개, 웹 2개)를 사용하는 것입니다. 실행되지 않는 웹 컨테이너를 업데이트한 후, 업데이트가 완료되면 해당 컨테이너를 사용하는 컨테이너로 전환하는 방식입니다.

이렇게 하면 말이 되는 것 같습니다. 즉, 데이터 컨테이너는 런처를 통해 리빌드를 실행하지 않는다는 뜻인가요? 저는 호스트 레벨의 Nginx를 통해 로드 밸런싱을 처리할 예정입니다. 다음 순서가 적절한지 확인해 주세요:

data container:

./launcher enter data_container 
SKIP_POST_DEPLOYMENT_MIGRATIONS=1 rake db:migrate

web_container

./launcher rebuild web_container1 && \
sleep 60 && ./launcher rebuild web_container2 

data container:

rails generate post_migration
SKIP_POST_DEPLOYMENT_MIGRATIONS=0 rake db:migrate

이 순서가 합리적인가요?

모든 것은 데이터 컨테이너에 어떤 업데이트가 필요한지에 따라 달라집니다.

Postgres 12 업데이트는 피할 수 없는 다운타임의 좋은 예입니다. 중복 데이터 컨테이너가 있더라도, 데이터베이스 업그레이드가 진행되는 동안에는 중복 사이트를 읽기 전용으로 실행해야 합니다.

다운타임이 전혀 없게 하는 유일한 방법은 업그레이드를 하지 않는 것입니다. 단일 컨테이너 설치에서 /admin/upgrade를 통해 수행되는 업데이트는 이미 제로 다운타임입니다. 베이스 이미지가 업데이트될 때와 같이 ssh를 통해 수행되는 업데이트는 예산과 복잡성에 대한 허용 범위에 따라 다운타임의 정도가 달라집니다.

다운타임을 피하는 가장 좋은 방법은 스테이징 복사본을 구축하는 것이며, 그렇지 않으면 플러그인이나 커스터마이징에서 호환성 문제가 발생할 때마다 업데이트 후 작은 다운타임 위험을 감수해야 합니다.

좋습니다. 따라서 큰 문제가 발생하지 않도록 스테이징 환경에서 실행을 한 번 해보고 결과를 관찰해 보겠습니다… 즉, 위의 절차를 시도해 보고 데이터 컨테이너가 실패하는지 확인하는 것이죠?

만약 그렇다면 스테이징은 데이터 1개, 웹 1개로 구성하고, 프로덕션은 데이터 2개, 웹 2개로 구성할 수 있습니다. 스테이징에서 먼저 시도했을 때의 최악의 시나리오라면 프로덕션에서는 다음과 같이 진행할 수 있습니다:

  • read-only 설정
  • cp -rp shared/data1을 shared/data2로 복사
  • data2 업그레이드
  • web2 중지
  • data2를 web2에 연결
  • web2 재구축
  • data2를 web1에 연결
  • web1 재구축
  • read-only false 설정

이렇게 이해하면 맞습니까?

다운타임에 대한 정의에 따라 다릅니다.

사용자가 사이트에 접근할 수 없다면 당연히 다운타임이겠죠.

그렇다면 가입, 게시글 작성, 댓글 작성, 좋아요 기능이 작동하지 않는 경우도 다운타임으로 보시겠습니까?

대규모 커뮤니티라면 SSD에 여러 데이터 컨테이너를 실행하는 비용이 적지 않을 것입니다. Amazon RDS와 같은 외부 PostgreSQL 서버를 고려해 보셨나요?

@Stephen이 지적하는 세부 사항은 정말 중요합니다. 예를 들어, *제로 다운타임(zero downtime)*이 무엇인지 정확히 이해해야 하기 때문입니다. 제로 다운타임 요건을 다음과 같은 방식으로 우회하는 것도 가능합니다:

제로 다운타임을 "요청이 유효할 때 HTTP 200 외의 코드로 사용자에게 응답하지 않는 것(필요에 따라 300과 400은 유지)"으로 정의합니다. 그런 다음 Discourse를 10달러짜리 드롭렛(droplet)에 단일 컨테이너 솔루션으로 배포하고, 500 에러가 발생하지 않도록 하기 위해 https://meta.discourse.org/t/adding-an-offline-page-when-rebuilding/45238을 추가합니다. 이렇게 하면 다운된 사이트가 표시되지 않습니다.

합리적인 사고를 가진다면 이것이 제로 다운타임이라고 생각할까요? 절대 아닙니다. 제안된 대로 작동하나요? 물론입니다. 그리고 더 제로 다운타임 안전(zero downtime proof) 하도록 다른 지역에 스탠바이 서버를 추가할 수도 있습니다.

그것이 바로 자격(qualifications)과 의미(semantics)가 중요한 이유입니다. 항상 무언가를 표시하는 것과 사이트의 기능이 항상 유지되는 것은 같은 개념이 아닙니다.

좀 더 이해를 돕기 위해 몇 가지 여쭤볼게요. 제로 다운타임(무중단) 목표를 달성하기 위해 어떤 조건이 필요하신가요? 사용자가 10~30분 정도 읽기 전용(read-only) 상태인 것을 감수할 수 있나요? 해킹 수준의 기술력을 갖추셔서 임시 해결책을 직접 만들 수 있나요? 아니면 '유지보수 중, 곧 돌아올게요’라는 안내 페이지를 사용자에게 보여줄 방법을 찾고 계신가요? 여러분에게 실제로 유용한, 보다 정확한 해결책을 제시하거나 적어도 올바른 방향으로 안내해 드리려면 더 자세한 정보가 필요합니다.