토픽 : Docker
Docker 의 개념
Docker 와 VM 의 비교
실습 : Docker 를 이용하여 Hello NORA! 페이지 만들어 보기
Go언어로 작성된 리눅스 컨테이너 기반으로 하는 오픈소스 가상화 플랫폼으로 컨테이너 기술을 사용하여 애플리케이션의 실행 환경을 구축 및 운용하기 위한 플랫폼으로 애플리케이션 실행에 필요한 것을 하나로 모아두고 그 이미지를 사용하여 다양한 환경에서 애플리케이션 실행환경을 구축 및 운용하기 위한 오픈소스 플랫폼이다.
Docker는 가상 머신처럼 독립된 실행환경을 만들어주는 것으로 운영체제를 설치하는 것과 유사한 효과를 낼 수 있지만, 실제 운영체제를 설치하지 않기 때문에 설치 용량이 적고 실행 속도 또한 빠르다. 예전에는 윈도에 VM Ware와 같은 가상 머신을 설치하였으나 최근에는 리눅스 계열에서 Docker가 그 역할을 대신하고 있다.
도커 컨테이너는 일종의 소프트웨어를 소프트웨어의 실행에 필요한 모든 것을 포함하는 완전한 파일 시스템 안에 감싼다. 여기에는 코드, 런타임, 시스템 도구, 시스템 라이브러리 등 서버에 설치되는 무엇이든 아우른다. 이는 실행 중인 환경에 관계 없이 언제나 동일하게 실행될 것을 보증한다.
도커를 설치하면 Docker 이미지를 각각의 환경에 똑같이 적용할 수 있다.
[일반적인 시스템 개발 흐름]
[Docker를 사용한 시스템 개발 흐름]
향상된 컴퓨터의 성능을 더욱 효율적으로 사용하기 위해 가상화 기술이 많이 등장한다.
서버 관리자 입장에서 CPU사용률이 10%대 밖에 되지 않는 활용도가 낮은 서버들의 리소스 낭비일 수밖에 없고 모든 서비스를 한 서버안에 올리면 안정성에 문제가 생길 수 있다. 그래서 안정성을 높이며 리소스도 최대한 활용할 수 있는 방법이 서버 가상화이다. 모두가 아는 대표적인 가상화 플랫폼으로는 VM이 있다.
컨테이너는 격리된 공간에서 프로세스가 동작하는 기술로 가상화 기술의 하나로 대표적으로 LXC(Linux Container)가 있다. 기존 OS를 가상화 시키던 것과 달리 컨테이너는 OS레벨의 가상화로 프로세스를 격리시켜 동작하는 방식으로 이루어진다.
호스트 OS상에 논리적인 컨테이너를 만들고 애플리케이션을 작동하기 위해 필요한 라이브러리나 애플리케이션등을 하나로 모아 별도의 서버 처럼 사용할 수 있게 한다.
한 서버의 여러 OS를 가상화 하여 사용하는 것과 컨테이너 방식으로 프로세스를 격리시켜 동작하는 방법은 어떠한 차이가 있을까?
우리에게 익숙한 VMware나 VirtualBox같은 가상머신은 Host OS 위에 가상화를 시키기 위한 Hypervisor 엔진 그리고 그 위에 Guest OS를 올려 사용한다. 이는 가상화된 하드웨어 위에 OS가 올라가는 형태로 거의 완벽하게 Host와 분리된다고 봐도 무방하다. 이 방식은 여러가지 OS를 가상화(윈도우에서 리눅스를 돌린다던가) 할 수 있고 비교적 사용법이 간단하지만 무겁고 느려서 운영환경에선 사용할 수 없다. (주로 테스트 환경 구축용으로 사용한다.)
반면에 컨테이너 기반 가상화는 Docker 엔진 위에 Application 실행에 필요한 바이너리만 올라가게 된다. OS 가상화를 보면 Host OS와 완전히 분리되는 장점은 있지만 OS위에 OS를 올리기 때문에 무겁고 느릴수 밖에 없다. 하지만 컨테이너 기반 가상화는 Host OS 그리고 Docker 엔진위에서 바로 동작하며 Host의 커널을 공유한다. 커널을 공유하게 되면 io처리가 쉽게 되어 성능의 효율을 높일 수 있다.
컨테이너 기반 가상화는 가상 머신을 생성하는 것이 아니라 Host OS가 사용하는 자원을 분리하여 여러 환경을 만들 수 있도록 한다.
OS가상화는 컨테이너기반 가상화보다 더 높은 격리 레벨을 지원한다. 이는 보안적인 측면에서 더욱 유리하고 커널을 공유하지 않기 때문에 멀티 OS가 가능하다.
그럼에도 왜 Docker를 쓰는가?
Docker는 다양하게 사용할 수 있다.
실무에서는 우분투 환경에 CentOS container를 설치하여 사용하거나, 이미 검증된 Web server의 설정 및 Binary가 설치된 container를 설치하여 복잡한 configuration 과정을 줄일 수 있다.
Docker는 하나의 Configuration으로 모든 플랫폼에서 실행할 수 있다.
Configuration 파일을 코드에 넣고 환경 변수를 전달하여 다른 환경에 맞출 수 있다.
따라서 하나의 Docker 이미지를 다른 환경에서 사용할 수 있다.
Docker는 일관된 환경을 제공하여 개발 및 코딩을 훨씬 편안하게 만들어준다.
Docker 이미지는 변경이 불가하기에 개발환경에서 운영 환경까지 애플리케이션 환경이 변경되지 않는 이점이 존재한다. 개발 생산성 향상 개발 환경을 운영 환경에 최대한 가깝게 복제할 수 있다.
Docker를 사용하면 코드가 운영 환경의 컨테이너에서 실행될 수 있으며 VM과 달리 Docker는 오버 헤드 메모리 용량이 적기에 여러 서비스를 실행하는데 도움이 된다. 또한 Docker의 Shared Volume을 사용하여 호스트에서 컨테이너의 어플리케이션 코드를 사용할 수 있도록 할 수 있다. 이를 통해 개발자는 자신의 플랫폼 및 편집기에서 소스 코드를 편집할 수 있으며 이는 Docker내에서 실행 중인 환경에 반영된다.
Web Server(e.g. Apache, Nginx)와 연결된 API 서버를 격리할 필요가 있는 경우가 있다. 이 경우 다른 컨테이너에서 API를 서버를 실행할 수 있다.
컨테이너가 OS를 부팅하지 않고 어플리케이션을 실행하기 때문에 Docker 컨테이너를 매우 빠르게 만들 수 있다.
Docker Image란 컨테이너를 실행할 수 있는 실행파일, 설정 값 들을 가지고 있는 것이다.
그림과 같이 Image를 컨테이너에 담고 실행을 시킨다면 해당 프로세스가 동작하게 된다.
그럼 어떻게 이미지가 만들어지는가?
ubuntu 이미지를 만들기 위해 Layer A,B,C가 들어간다.
그럼 nginx 이미지를 만든다고 생각했을땐 어떻게 될까요?
이미 Layer A,B,C로 만들어진 ubuntu 이미지를 베이스 이미지로 사용하여 베이스 이미지에 nginx만 더하게 된다. 그렇다면 실질적으로 Layer A, B, C, nginx 가 더해진 것이지만 과정은 unbuntu + nginx가 더해진 것이다.
그렇다면 web app 이미지를 만들려고 할 땐 어떻게 될까요?
ubuntu 이미지에 nginx를 올리고 web app을 올리는 것이 아닌 이미 만들어진 nginx 베이스 이미지에 web app을 올려 이미지를 만들게 된다.
Docker Image들을 저장하고 배포하는 Docker Hub는 정말 잘 활성화 되어있다.
이미 여러 회사들은 소프트웨어를 Docker Hub를 통해 배포하기 시작했고 우린 Docker hub에서 image를 pull하여 간단하게 컨테이너에 넣어 사용할 수 있다.
만약 배포판이 없거나 보완하고 싶다면? Docker Fille 사용한다.
Docker File은 이미지 생성 출발점으로 이미지를 구성하기 위한 명령어들을 작성하여 이미지를 구성할 수 있다. 그 뜻은 Docker File을 읽을 수만 있다면 해당 이미지가 어떻게 구성되어 있는지도 알 수 있다는 의미이다.
FROM jdk8:latest
WORKDIR /app
RUN mkdir /app/nexus-2.14.9-01
RUN mkdir /app/sonatype-work
RUN yum -y install httpd
ENV JAVA_HOME /usr/local/jdk1.8.0_181
ENV PATH=$JAVA_HOME/bin:$PATH
ENV CLASSPATH=.
EXPOSE 3411
ADD run.sh /app/
CMD ["/app/run.sh"]
Docker Hub에서는 이미지를 저장하고 관리해준다.
위에서도 많은 회사들이 Docker로 소프트웨어를 배포하기 시작했고 공개이미지들을 공유할 수 있다. Docker Hub를 이용하면 손쉽게 imaer를 pull 받아 컨테이너에 적용 시킬 수 있다. (GitHub와 동일하게 생각해도 된다.)
그렇다면 Docker Registry는 무엇일까?
Docker Hub처럼 공개된 방식이 아닌 비공개적으로 구축한 격리된 저장소이다.
Docker Image를 Pull받기 위한 url 이다. 그림과 같이 앞에있는 url을 적지 않으면 default로 Docker Hub에서 Image를 pull 받게되고 url을 적어준다면 사설 저장소에서 이미지를 받을 수 있다.