[Docker] 컨테이너를 활용해 서버 관리하기

옹심이·2024년 12월 16일
0
post-thumbnail

컨테이너는 stateless하다

컨테이너가 실행된 후 발생하는 모든 변경 사항은 읽기 쓰기 전용 레이어인 컨테이너 레이어에 쌓이게 되 종료되는 순간 변경 사항이 모두 사라진다. 또한 컨테이너 이미지의 버전을 변경할 때도 실행중인 컨테이너를 삭제하고 새로운 이미지로 실행시켜야 하며 기존에 컨테이너 레이어에 쌓이 내용들도 모두 삭제된다.

만약에 상태가 존재한다면 컨테이너가 변경 또는 추가될 때 이러한 상태들 하나하나를 모두 관리해줘야한다. 하지만 컨테이너는 stateless하기 때문에 쉽게 수를 증가시킬 수 있고, 다른 환경에서 빠르게 배포할 수 있다.

엔터프라이즈 환경에서 운영되는 서버를 업데이트할 때 이러한 성격이 중요하게 작용한다.

만약 같은 서버가 10대를 한번에 업데이트해야 한다면 서버에 접근 후 기존 어플리케이션을 중지시키고 새로운 버전의 어플리케이션을 덮어쓰기한 후 다시 실행시킬수 밖에 없다.

또한 10대의 서버에 대해 각 서버에 대해서 변경 사항을 동일하게 적용 시켜야 하기 때문에 부작용이 발생할 가능성이 높으며, 실제 실행중인 서버에 변경 사항을 적용한다는 점 또한 안정적이지 않다.

하지만 컨테이너 자체는 상태를 가지지 않으며 모든 상태는 이미지에 저장되기 때문에, 어플리케이션에 대한 업데이트 사항은 전부 새로운 이미지로 생성하여 컨테이너를 새로 만들어야한다.

그렇기 때문에 실행중인 서버에 직접 접근하여 서버를 업데이트하는 것이 아니라, 새로운 버전의 이미지를 만들어 배포하는것이다. 먼저 실행중이던 이전 버전의 컨테이너를 제거한다. 새로운 이미지로 컨테이너를 실행시킨다.

또한 도커 이미지와 레이어 포스트에서 봤던것 처럼, 컨테이너는 이미지에 읽기 쓰기 전용 레이어만 추가된 것이기 때문에 아주 빠르게 컨테이너 수를 증가 시킬 수 있으며 덕분에 트래픽 증가에도 더 유연하게 대처할 수 있다.

특징 정리

  1. 컨테이너의의 이미지는 한 번 지정된 후 변경되지 않는 불변성을 띈다. 그래서 새로운 버전의 컨테이너가 필요하면 이 컨테이너를 실행할 새로운 이미지를 만들어야 한다.
  2. 컨테이너는 언제든지 새로운 컨테이너로 대체할 수 있다. 컨테이너는 이미지 기반으로 실행되며 실제 실행되기 원하는 서버의 상태는 이미지에 저장되어 있으므로, 컨테이너를 종료하고 실행하는 것이 자유롭다.
  3. 컨테이너는 어떠한 환경에서도 실행할 수 있다. 예를 들어 개발 서버, 운영 서버 처럼 하나의 어플리케이션이 배포되는 여러가지 각각의 환경에서 제약 없이 컨테이너를 실행할 수 있다. 덕분에 트래픽 증가에도 더 유연하게 대처할 수 있다.

서버 방법론

클라우드 네이티브 환경에서 MSA 아키텍처로 개발이 이뤄지며 구조상 서버의 개수가 아주 많다. 앞서 다뤘던 컨테이너의 stateless한 상태는 클라우드 네이티브 환경에 아주 적합하다.

전통적인 서버 방법론인 Pet방식과 컨테이너 사용이 적합한 Cattle방식을 비교해보자.

Pet 방식
Pet은 말그대로 가정에서 키우는 애완 동물을 의미한다.
실제로 애완 동물처럼 서버 하나를 소중하게 관리하는 방법론이다.
Pet 방식세어는 서버에 발생하는 문제와 종료가 서비스 장애라고 여기기 때문에, 항상 서버의 상태를 주시하고 관리한다.

Cattle 방식
Cattle 은 목장에서 키우는 가축을 의미한다.
Cattle 방식은 서버를 일종의 소모품으로 생각한다.
서버에 에서가 발생하거나 서버가 갑자기 종료되는 일은 충분히 일어날 수 있는 일이라고 생각하기 때문에, 서버가 종료되면 서버를 빠르게 다시 실행시켜서 기존 서버를 대체하는 방식이다.
빠르게 서버를 늘리거나, 기존 서버를 새로운 서버로 대체하기 위해서는 서버가 stateless한 것이 좋다.

컨테이너를 사용한 어플리케이션 개발 시 주의점

DB 서버를 따로 사용하자

컨테이너 자체는 상태가 없기 때문에 데이터를 영구적으로 저장하기 위한 별도의 데이터베이스 서버가 필요하다. 저장 또는 공유가 필요한 데이터는 무조건 외부에 저장해야하기 때문이다.

예를 들어, 사용자가 요청한 내용을 파일로 저장해야하는 로직이 있을 때를 가정해보자.

파일을 저장한 컨테이너가 중단 또는 재생성 되는 경우 컨테이너의 읽기 쓰기 레이어가 초기화되므로 데이터를 유지할 수 없다.

그래서 중요한 데이터는 어플리케이션 서버에 보관하는 것보다 외부 데이터베이스에 저장하는 것이 바람직하다.

상태 저장을 위한 데이터를 외부에 저장하자

사용자의 세션 정보, 캐시 등의 정보도 외부에 저장해야한다.

예를 들면 로그인 정보, 즐겨찾기 리스트 등의 정보는 임시로 저장을 해두어야 한다. 주로 캐시 서버와 브라우저의 쿠키를 통해 관리할 수 있으며, DB 서버와 마찬가지로 어플리케이션 서버에 보관하지 않는 것이 좋다

동일한 요청에는 동일한 응답

서버를 여러 대 실행했을 때 각각의 서버마다 다른 응답을 제공하면 안된다.

트래픽 증가에 따라 여러 대로 어플리케이션 서버를 둘 수 있는데, 만약 동일한 요청에 다른 내용으로 응답한다면 이는 stateless한 속성을 어플리에키션에서 해치고 있다고 볼 수 있다.

환경 변수와 구성 파일을 외부에서 주입한다

컨테이너 자체는 상태를 가질 수 없지만, 이 이미지를 컨테이너로 실행할 때 어떤 cmd값을 주고 어떤 환경 변수를 주입하는지에 따라 완전히 다른 어플리케이션이 된다.

따라서 컨테이너 실행하는 시점의 메타데이터 값을 설정해 환경 변수를 주입하여 컨테이너를 구성해야한다.

0개의 댓글