본 포스트는 Inflearn '따라하며 배우는 도커와 CI환경' 강의를 기반으로 작성되었습니다.
일반적으로 프로그램을 설치하고 실행하는 과정에 있어서 직접 개발을 한 프로그램이 아니라면 보유 서버, 패키지 버전, OS 등등 여러 환경에 따라 프로그램 실행 및 설치 과정에서 많은 에러가 발생하기도 하고 버전 간의 문제로 인해 추가 패키지 설치 등 그 과정이 굉장히 복잡해지기도 합니다.
그래서 이러한 과정을 쉽게 하기 위해 환경에 대한 정보들도 싸그리 담아서 이미지로 만들어서 컨테이너를 구성하자는 툴이 도커!
컨테이너를 사용해 응용프로그램을 만들고, 배포하고, 실행하는 과정을 더 쉽게 할 수 있도록 설계된 도구. 컨테이너 기반의 오픈소스 가상화 플랫폼이자 생태계.
Then...
다양한 프로그램, 실행환경을 추상화한 개념으로 동일한 인터페이스를 제공하여 프로그램의 배포 및 관리를 단순하게 해줌!
-> 도커 이미지는 프로그램을 실행하는 데 필요한 설정이나 환경을 갖고 있으며, 도커 이미지를 기반으로 컨테이너를 생성한다. 그리고 그 컨테이너를 이용해서 프로그램을 실행한다!
MacOS(M1 Chip) 기반입니다~
도커 사용 방식 흐름은 다음과 같습니다.
한 번 Hello-world라는 이미지를 기반으로 프로그램을 실행해보겠습니다.
shell에 'docker run hello-world' 명령어를 입력할 경우, 위와 같은 로그가 뜨게 되는데요. 우선 local 내에 hello-world관련 image가 존재하지 않는다는 것을 확인한 후, docker hub라는 storage에서 hello-world라는 image를 받아오게 됩니다. 이 과정에 찾고자 하는 image가 hub에 존재하지 않는다면 당연히 다운로드가 되지 않습니다. hello-world의 경우 해당문구가 모든 코딩의 시발점인 만큼 Docker에 대한 설명을 print해주는 프로그램으로 구성이 되어있습니다.
여기서 만약 docker run hello-world를 한 번 더 실행시켜준다면 이미 local에 hello-world라는 image가 존재하기 때문에 추가적인 다운로드 없이 위 프로그램이 바로 실행되게 됩니다.
위에서 정리한 바에 의하면 컨테이너의 역할은 가상머신과 굉장히 유사하다는 점을 알 수가 있습니다. 하지만, Container와 VM은 명백히 다른 개념이고 Container가 더 가벼운 SW라고 배웠는데요. 이 부분에 대해서 좀 더 세세히 다뤄보겠습니다.
우선 두 시스템의 공통점은 다음과 같습니다. 도커 컨테이너와 가상 머신은 기본 하드웨어 관점에서 격리된 환경에 응용 프로그램을 배치하는 방식이라는 점이 공통점입니다. 차이점에 대해서는 가장 큰 차이점은 위의 공통점에서 언급한 격리라는 개념에 있어서 그 정도의 차이라고 합니다. 두 개념을 그림으로 표현하면 다음과 같습니다.
잘 그렸죠?
위에서도 언급했듯이 Container는 VM에 비해 가벼운 SW라고 말씀드렸는데, 그 이 유를 위 그림에서 확인할 수 있습니다. 우선, VM의 경우에는 Guest OS를 달고 있습니다. 또한 Host OS와의 중간 단계로서 HyperVisor와 Docker Engine은 각각 달고 있지만, 제가 찾아 본 아래 표에 의하면 Hypervisor가 훨씬 무거운 개념인 것 같습니다.
또한 강의에서 설명해준 내용인데 하나의 프로그램을 실행하는 관점에서 Docker의 경우에는 Host OS 위에 image를 배포만 해주면 끝이지만 VM의 경우에는 VM을 띄우고 자원을 할당하고 Guest OS를 부팅시켜야 하는 복잡한 과정이 존재한다고 합니다.
추가 특이점으로는 같은 Host OS 내에 있는 Container들은 kernel을 공유하지만, VM같은 경우는 독자적인 Guest OS를 사용하기 때문에 kernel이 격리되어 있다고 합니다.
VM의 경우에는 독자적인 OS를 구축하는 방식으로 격리를 일궈냈다면...
이 개념에 대해 알기 위해서는 C group과 네임스페이스라는 개념이 필요합니다. 이 개념들은 Container와 Host 위에서 구동되는 Process들간의 벽을 만드는 리눅스 커널의 기능들입니다.
C Group이란 Control Groups의 준말로 정해진 CPU 시간, 메모리 할당, 네트워크 대역폭과 같은 자원을 특정 프로세스 그룹에 할당할 수 있는 개념입니다.
Namespace는 하나의 시스템에서 프로세스를 격리시킬 수 있는 경량 가상화 기술이라고 합니다.
저는 Software의 영역에서는 Namespace를 통해 고립을, Hardware Resource 영역에서는 C Group 기술을 이용해 고립을 구현했다고 이해하였습니다.
이미지는 응용 프로그램을 실행하기 위한 모든 정보를 담고 있습니다. 이 정보는 두 가지로 나뉘어지는데요. 바로 프로그램을 실행하기 위한 명령어와 해당 응용 프로그램/응용 프로그램을 실행하기 위해 필요한 프로그램들의 파일 스냅샷입니다. 이러한 정보들을 기반으로 컨테이너를 만드는 순서는 다음과 같습니다.
https://www.inflearn.com/course/따라하며-배우는-도커-ci
https://www.hitechnectar.com/blogs/hypervisor-vs-docker/