Docker는 가상 머신과 어떻게 다릅니 까?


3692

Docker와 전체 VM의 차이점을 이해하기 위해 Docker 설명서 를 계속 읽으 십시오 . 무겁지 않고 완전한 파일 시스템, 격리 된 네트워킹 환경 등을 제공하는 방법은 무엇입니까?

일관된 프로덕션 환경에 단순히 배포하는 것보다 소프트웨어를 Docker 이미지에 배포하는 것이 왜 쉬운가?


11
Docker vs KVM 성능 분석 : bodenr.blogspot.com/2014/05/…
HDave

1
당신이 그들의 이미지의 차이를 찾고 있다면 - stackoverflow.com/questions/29096967/...을
devesh-ahuja

21
Docker는 가상 머신이 아니며 구성 관리 도구입니다.
aaa90210

3
간단히 말해서 : 서버 가상화를 원하지만 웹 응용 프로그램 만 실행하려는 경우 VM-> 3 개의 가상 계층을 실행하여 앱 실행을 허용해야합니다. DOCKER-> 실제 CPU와 웹 응용 프로그램 사이에 하나의 레이어 만 있습니다. 내가 추천하는 사람들을 가상화하기 위해 웹 애플리케이션을 실행해야하는 경우 더욱 강력하고 더 나은 복제 / 미러링
Davide Castronovo

6
Docker for Mac 및 Docker for Windows가 가상화 계층을 사용한다는 것을 잊지 마십시오.
Shapeshifter

답변:


3434

Docker는 원래 LinuX Containers (LXC)를 사용했지만 나중에 호스트와 동일한 운영 체제에서 실행되는 runC (이전의 libcontainer ) 로 전환했습니다 . 이를 통해 많은 호스트 운영 체제 리소스를 공유 할 수 있습니다. 또한 계층 파일 시스템 ( AuFS )을 사용하고 네트워킹을 관리합니다.

AuFS는 계층 파일 시스템이므로 함께 병합 된 읽기 전용 부분과 쓰기 부분을 가질 수 있습니다. 하나는 운영 체제의 공통 부분을 읽기 전용 (모든 컨테이너간에 공유)으로 설정 한 다음 각 컨테이너에 쓰기를위한 고유 한 마운트를 제공 할 수 있습니다.

따라서 1GB 컨테이너 이미지가 있다고 가정하겠습니다. 전체 VM을 사용하려면 원하는 1GB x 개수의 VM이 있어야합니다. Docker와 AuFS를 사용하면 모든 컨테이너간에 1GB의 대량을 공유 할 수 있으며 컨테이너가 1000 개인 경우 컨테이너 OS에 대해 1GB 이상의 공간이 남아있을 수 있습니다 (모두 동일한 OS 이미지를 실행한다고 가정) .

완전 가상화 시스템은 자체 리소스 세트를 할당받으며 최소한의 공유를 수행합니다. 더 많은 격리를 얻지 만 훨씬 더 무겁습니다 (더 많은 리소스가 필요함). Docker를 사용하면 격리가 줄어들지 만 컨테이너는 가벼워집니다 (더 적은 리소스 필요). 따라서 호스트에서 수천 개의 컨테이너를 쉽게 실행할 수 있으며 깜박 거리지 않습니다. Xen을 사용하여 시도해보십시오. 정말로 큰 호스트가 없다면 가능하지 않다고 생각합니다.

전체 가상화 시스템은 일반적으로 시작하는 데 몇 분이 걸리지 만 Docker / LXC / runC 컨테이너는 몇 초가 걸리고 종종 1 초도 채 걸리지 않습니다.

각 가상화 시스템 유형마다 장단점이 있습니다. 보장 된 리소스로 완벽한 격리를 원한다면 완전한 VM이 필요합니다. 프로세스를 서로 분리하고 합리적인 크기의 호스트에서 수많은 프로세스를 실행하려면 Docker / LXC / runC가 좋은 방법입니다.

자세한 내용 은 LXC 작동 방식을 잘 설명하는 이 블로그 게시물 을 확인하십시오 .

일관된 프로덕션 환경에 단순히 배포하는 것보다 소프트웨어를 도커 이미지 (적절한 경우)에 쉽게 배포하는 이유는 무엇입니까?

일관된 프로덕션 환경을 배포하는 것이 말하는 것보다 쉽습니다. ChefPuppet 과 같은 도구를 사용하더라도 항상 호스트와 환경간에 변경되는 OS 업데이트 및 기타 사항이 있습니다.

Docker를 사용하면 OS를 공유 이미지로 스냅 샷 할 수 있으며 다른 Docker 호스트에 쉽게 배포 할 수 있습니다. 로컬로 dev, qa, prod 등 : 모두 동일한 이미지. 물론 다른 도구를 사용하여이 작업을 수행 할 수 있지만, 쉽고 빠르지는 않습니다.

이것은 테스트에 좋습니다. 데이터베이스에 연결해야하는 수천 개의 테스트가 있고 각 테스트에는 데이터베이스의 원시 복사본이 필요하며 데이터를 변경한다고 가정 해 봅시다. 이에 대한 고전적인 접근 방식은 모든 테스트 후에 사용자 지정 코드 또는 Flyway 와 같은 도구를 사용하여 데이터베이스를 재설정하는 것입니다. 시간이 많이 걸리고 테스트를 순차적으로 실행해야합니다. 그러나 Docker를 사용하면 데이터베이스 이미지를 생성하고 테스트 당 하나의 인스턴스를 실행 한 다음 모든 테스트가 데이터베이스의 동일한 스냅 샷에 대해 실행될 것이므로 모든 테스트를 병렬로 실행할 수 있습니다. 테스트가 병렬로 실행되고 Docker 컨테이너에서 실행되므로 동일한 상자에서 모두 동시에 실행할 수 있으며 훨씬 빠르게 완료됩니다. 완전한 VM을 사용하여 시도하십시오.

댓글에서 ...

흥미 롭습니다! 나는 여전히 "OS 스냅 샷 [ting]"이라는 개념에 혼란스러워하고 있다고 생각한다. OS의 이미지를 만들지 않고도 어떻게 할 수 있습니까?

글쎄, 내가 설명 할 수 있는지 보자. 기본 이미지로 시작한 다음 변경하고 docker를 사용하여 해당 변경 사항을 커밋하면 이미지가 생성됩니다. 이 이미지에는 밑면과의 차이점 만 포함되어 있습니다. 이미지를 실행하려면 기본도 필요하며 계층 파일 시스템을 사용하여 기본 위에 이미지를 계층화합니다. 위에서 언급 한 것처럼 Docker는 AuFS를 사용합니다. AuFS는 서로 다른 레이어를 병합하여 원하는 것을 얻습니다. 당신은 그것을 실행해야합니다. 점점 더 많은 이미지 (레이어)를 계속 추가 할 수 있으며 diff 만 계속 저장합니다. Docker는 일반적으로 레지스트리 에서 기성품 이미지 위에 빌드하므로 전체 OS를 "스냅 샷"할 필요가 거의 없습니다.


239
Ken, 어떤 곳에서는 OS와 커널을 연결합니다. 호스트의 모든 컨테이너는 동일한 커널에서 실행되지만 나머지 OS 파일은 컨테이너마다 고유 할 수 있습니다.
Andy

22
흥미 롭습니다! 나는 여전히 "OS 스냅 샷 [ting]"이라는 개념에 혼란스러워하고 있다고 생각한다. OS의 이미지를 만들지 않고도 어떻게 할 수 있습니까?
zslayton

7
@ murtaza52 그들은 다른 파일 시스템에 대한 지원을 추가하고 있으므로 Aufs는 문제가되지 않습니다. 32 비트 지원이 언제 추가 될지 확실하지 않은 경우, 수요가 많지 않다고 생각하므로 우선 순위가 낮지 만 틀릴 수 있습니다.
Ken Cochrane

21
@Mike : ... 의심 할 여지없이 FreeBSD 교도소 에서 영감을 받았습니다HISTORY The jail utility appeared in FreeBSD 4.0.
Stefan Paletta

21
@Mike에 대한 의견이 궁금해하는 사람들은 삭제 된 것처럼 보이므로 다음과 같습니다. : Solaris 컨테이너. 2004 년으로 거슬러 올라갑니다 ... 이것은 혁신적인 개념이며 실제로 성능이 뛰어난 저렴한 호스팅 가상 머신을 수행 할 수있는 훌륭한 방법입니다. Joyent는 내가 처음으로 알고 있었다 ...>
Jeffrey 'jf'Lim

559

좋은 답변입니다. 컨테이너와 VM의 이미지 표현을 얻으려면 아래 이미지를 살펴보십시오.

여기에 이미지 설명을 입력하십시오

출처


20
<strike> 내가 이해하는 한 "docker engine"위에는 공유 리눅스 커널이 있어야한다. 그런 다음 일반적으로 공유 저장소 / 라이브러리가 있습니다. 그 후 먼저 각 컨테이너에 특정한 bins / libs 및 앱이 제공됩니다. 내가 틀렸다면 정정 해주세요. </ strike> 내가 틀 렸습니다. Docker 이미지는 커널을 호스트와 공유합니다 ( superuser.com/questions/889472/… 참조) . 그러나 컨테이너의 통합 파일 시스템을 설명하기 위해 docker 엔진 바로 위에 libs / bin의 공유 계층이있을 수 있습니다.
Betamos December

13
하이퍼 바이저를 베어 메탈 / 인프라에 설치할 수 있지만 Docket을 설치할 수 없기 때문에 위의 그림에 문제가 있습니다.
레자

@reza, Hypervisor를 Bare metal에 설치할 수 있다는 데 동의하지만 앱의 컨테이너화 및 일부 시나리오에 필요하지 않거나 적용 할 수없는 가상화를 제한하거나 피하는 방법에는 Docker가 권장됩니다. Ken Cochrane는 이것을 자세히 설명합니다. stackoverflow.com/a/16048358/2478933
manu97 2016 년

4
이것은 Docker Engine 이 무엇인지 명확하지 않습니다 . 매우 추상적 인 그림.
kyb

9
컨테이너와 커널 사이에 "Docker Engine"레이어가 없으며 컨테이너는 커널 (네임 스페이스, cgroup 등)에서 특별한 설정을 가진 프로세스입니다.
Paweł Prażak

504

가상화 및 컨테이너가 낮은 수준에서 작동하는 방식을 이해하면 도움이 될 수 있습니다. 그것은 많은 것들을 정리할 것입니다.

참고 : 아래 설명에서 약간 단순화하고 있습니다. 자세한 내용은 참조를 참조하십시오.

가상화가 낮은 수준에서 어떻게 작동합니까?

이 경우 VM 관리자는 CPU 링 0 (또는 최신 CPU의 "루트 모드")을 인계 받아 게스트 OS가 수행 한 모든 권한있는 호출을 가로 채서 게스트 OS에 자체 하드웨어가 있다는 환상을 만듭니다. 재미있는 사실 : 1998 년 이전에는 이런 종류의 가로 채기를 수행 할 방법이 없었기 때문에 x86 아키텍처에서는이를 달성하는 것이 불가능하다고 생각되었습니다. VMWare의 사람들 은 처음이었습니다 이를 위해 게스트 OS의 특권 호출을 위해 실행 가능 바이트를 메모리에 다시 쓰는 아이디어를 가진 사람이 이었습니다.

결과적으로 가상화를 통해 동일한 하드웨어에서 완전히 다른 두 개의 OS를 실행할 수 있습니다. 각 게스트 OS는 부트 스트래핑, 커널로드 등의 모든 프로세스를 거칩니다. 예를 들어 게스트 OS는 호스트 OS 또는 다른 게스트에 대한 전체 액세스 권한을 얻지 못하고 엉망이 될 수 있습니다.

컨테이너가 낮은 수준에서 어떻게 작동합니까?

2006 년경 Google 직원 일부를 포함하여 사람들은 네임 스페이스 라는 새로운 커널 레벨 기능을 구현했습니다 (그러나 그 아이디어 는 FreeBSD에 오래 전부터 존재했습니다)). OS의 기능 중 하나는 네트워크 및 디스크와 같은 글로벌 리소스를 프로세스와 공유 할 수 있도록하는 것입니다. 이러한 전역 리소스가 네임 스페이스로 래핑되어 동일한 네임 스페이스에서 실행되는 프로세스에만 표시되도록하려면 어떻게해야합니까? 디스크 덩어리를 가져 와서 네임 스페이스 X에 넣은 다음 네임 스페이스 Y에서 실행중인 프로세스는 볼 수 없거나 액세스 할 수 없습니다. 마찬가지로 네임 스페이스 X의 프로세스는 네임 스페이스 Y에 할당 된 메모리의 아무것도 액세스 할 수 없습니다. 물론 X의 프로세스는 네임 스페이스 Y의 프로세스를 보거나 대화 할 수 없습니다. 이는 전역 리소스에 대한 일종의 가상화 및 격리를 제공합니다. 도커 작동 방식은 다음과 같습니다. 각 컨테이너는 고유 한 네임 스페이스에서 실행되지만 정확히 동일한다른 모든 컨테이너로 커널. 커널은 프로세스에 할당 된 네임 스페이스를 알고 있기 때문에 API 호출 중에 프로세스가 자체 네임 스페이스의 리소스에만 액세스 할 수 있도록합니다.

컨테이너와 VM의 한계는 이제 분명합니다. VM과 같은 컨테이너에서 완전히 다른 OS를 실행할 수는 없습니다. 그러나 동일한 커널을 공유하기 때문에 Linux의 다른 배포판을 실행할 수 있습니다 . 격리 수준은 VM만큼 강력하지 않습니다. 실제로 "게스트"컨테이너가 초기 구현에서 호스트를 인수 할 수있는 방법이있었습니다. 또한 새 컨테이너를로드 할 때 VM 에서처럼 새 OS의 전체 사본이 시작되지 않음을 알 수 있습니다. 모든 컨테이너 는 동일한 커널을 공유. 이것이 용기가 가벼운 이유입니다. 또한 VM과는 달리 새로운 OS 사본을 실행하지 않기 때문에 컨테이너에 상당한 양의 메모리를 사전 할당 할 필요가 없습니다. 이를 통해 하나의 OS에서 수천 개의 컨테이너를 샌드 박스 처리하는 동안 자체 VM에서 별도의 OS 사본을 실행하는 경우 불가능할 수 있습니다.


26
와우, 저수준의 설명과 역사적 사실에 감사드립니다. 나는 그것을 찾고 있었고 위에서 발견되지 않았다. "동일한 커널을 공유하기 때문에 Linux의 다른 배포판을 실행할 수 있습니다." 는 무슨 뜻입니까? ? 게스트 컨테이너가 정확히 동일한 Linux 커널 버전을 가지고 있거나 중요하지 않다고 말하고 있습니까? 게스트에서 OS 명령을 호출해도 게스트 커널에서만 지원되는 경우 문제가되지 않습니다. 또는 예를 들어 게스트 커널에서는 수정되었지만 호스트 커널에서는 수정되지 않는 버그가 있습니다. 모든 손님이 버그를 나타냅니다. 맞습니까? 손님이 패치되었지만.
Jeach

7
@Jeach : 컨테이너에는 자체 커널이 없으며 호스트 중 하나를 공유 / 사용하고 있습니다. 따라서 동일한 머신 / VM에서 다른 커널이 필요한 컨테이너를 실행할 수 없습니다.
user276648

2
질문 : Google 직원 중 일부는 1996 년경 네임 스페이스 커널 기능에 관여했지만 1998 년까지 Google이 설립되지 않았다고 썼습니다. 'Google 직원이되기 위해 계속 갈 사람들'이라는 의미입니까?
Martin Gjaldbaek 8

3
@martin-2006 년을 주목 해 주셔서 감사합니다. 또한 2002 년 이래 Linux에는 다양한 유형의 네임 스페이스가 존재했지만 컨테이너화의 기반을 마련한 것은 2006 년의 작업이었습니다. 답변을 참조로 업데이트했습니다.
Shital Shah

20
+1 이것은 명확한 답변이어야하며, 다른 답변은 약간의 설명을 제공하지만, 상향식 저수준 설명 만이이 기술이 어떻게 작동하는지 명확하게 설명 할 수 있습니다. '자체 네임 스페이스로 그룹화 된 프로세스 = 컨테이너'. 정말 고마워요, 지금 알아요
Tino Mclaren

328

나는 Ken Cochrane의 답변을 좋아합니다.

그러나 여기에 자세히 다루지 않은 추가 관점을 추가하고 싶습니다. 제 생각에는 Docker는 전체 프로세스에서도 다릅니다. VM과는 달리 Docker는 하드웨어의 최적의 자원 공유에 관한 것만이 아니며, 응용 프로그램 패키징을위한 "시스템"을 제공합니다 (마이크로 서비스 세트로는 바람직하지만 필수는 아님).

나에게 그것은 rpm, Debian 패키지, Maven , npm + Git 과 같은 개발자 중심 도구와 Puppet , VMware, Xen 과 같은 ops 도구 사이의 격차에 맞습니다 .

일관된 프로덕션 환경에 단순히 배포하는 것보다 소프트웨어를 도커 이미지 (적절한 경우)에 쉽게 배포하는 이유는 무엇입니까?

귀하의 질문은 일관된 프로덕션 환경을 가정합니다. 그러나 어떻게 일관성을 유지 하는가? 파이프 라인의 일부 단계 (> 10)의 서버 및 애플리케이션을 고려하십시오.

이를 동기화하기 위해 꼭두각시와 같은 것을 사용하기 시작합니다. Chef 또는 자체 프로비저닝 스크립트, 게시되지 않은 규칙 및 / 또는 많은 문서와 . 이론상 서버는 무한정 실행될 수 있으며 완전히 일관성 있고 최신 상태를 유지할 수 있습니다. 실습에서는 서버 구성을 완전히 관리하지 못하므로 구성 드리프트에 대한 범위가 넓고 실행중인 서버에 대한 예기치 않은 변경이 있습니다.

이것을 피하기 위해 알려진 패턴이 있습니다. 불변 서버있습니다. 그러나 불변의 서버 패턴은 사랑받지 못했습니다. 대부분 Docker 이전에 사용 된 VM의 한계 때문입니다. 응용 프로그램에서 일부 필드를 변경하기 위해 몇 기가 바이트의 큰 이미지를 다루고 큰 이미지를 옮기는 것은 매우 힘들었습니다. 이해할 수 있는...

Docker 에코 시스템을 사용하면 "소규모 변경 사항"(aus 및 Registry 덕분)을 기가 바이트 단위로 이동할 필요가 없으며 런타임시 응용 프로그램을 Docker 컨테이너에 패키징하여 성능을 잃을 염려가 없습니다. 해당 이미지의 버전에 대해 걱정할 필요가 없습니다.

그리고 마지막으로 Linux 랩톱에서도 복잡한 프로덕션 환경을 재현 할 수도 있습니다 (귀하의 경우 작동하지 않으면 전화하지 마십시오.)

물론 VM에서 Docker 컨테이너를 시작할 수 있습니다 (좋은 아이디어). VM 수준에서 서버 프로비저닝을 줄입니다. 위의 모든 내용은 Docker에서 관리 할 수 ​​있습니다.

PS While Docker는 LXC 대신 자체 구현 "libcontainer"를 사용합니다. 그러나 LXC는 여전히 사용 가능합니다.


1
rpm 및 dpkg와 같은 도구 그룹에 git을 포함시키는 것이 이상합니다. 배포 / 패키징 도구로 git과 같은 버전 제어 시스템을 사용하려는 시도가 많은 혼란의 원인이되기 때문에 이것을 언급합니다.
blitzen9872

2
그는 틀리지 않습니다 .git은 패키지 관리에 사용될 수 있습니다. 예를 들어 bower는 기본적으로 git 태그를 다운로드하기위한 멋진 cli입니다.
roo2

2
컨테이너에 포장 응용 프로그램은 흥미롭고 유효한 접근 방식입니다. 그러나 도커에 패키지하면 종속성이나 공유 라이브러리에 대한 직접적인 지원이 없기 때문에 이것은 과도합니다. 이것이 바로 Ubuntu Snap 및 Flatpak for Redhat과 같은 새로운 패키징 기술이 달성하려는 것입니다. 제 생각에, 이러한 패키징 기술 중 하나가 리눅스 패키징의 미래가 될 것입니다.
yosefrow

@ blitzen9872도 이에 동의합니다. 그러나 그것이 실습에서 배포하기 위해 너무 자주 사용 되었기 때문에 정확하게 언급되었습니다. 다시 나는 그것을 좋아하지 않습니다.
aholbreich

@yosefrow는 "오버 킬"을 정교하게한다. "불변 서버"패턴의 아이디어와 장점을 확인하십시오. 물론 몇 가지 단점이 있습니다 ... 과잉이 보인다면 사용하지 마십시오.
aholbreich

245

Docker는 가상화 방법이 아닙니다. 실제로 컨테이너 기반 가상화 또는 운영 체제 수준 가상화를 구현하는 다른 도구를 사용합니다. 이를 위해 Docker는 처음에 LXC 드라이버를 사용하고 libcontainer로 이동했으며 이제는 runc로 이름이 변경되었습니다. Docker는 주로 응용 프로그램 컨테이너 내부의 응용 프로그램 배포 자동화에 중점을 둡니다. 응용 프로그램 컨테이너는 단일 서비스를 패키징하고 실행하도록 설계되었지만 시스템 컨테이너는 가상 시스템과 같은 여러 프로세스를 실행하도록 설계되었습니다. 따라서 Docker는 컨테이너화 된 시스템에서 컨테이너 관리 또는 응용 프로그램 배포 도구로 간주됩니다.

다른 가상화와 어떻게 다른지 알기 위해 가상화와 그 유형을 살펴 보겠습니다. 그렇다면 차이점이 무엇인지 이해하는 것이 더 쉬울 것입니다.

가상화

고안된 형태로, 여러 애플리케이션을 동시에 실행할 수 있도록 메인 프레임을 논리적으로 나누는 방법으로 간주되었습니다. 그러나 회사와 오픈 소스 커뮤니티가 권한있는 명령을 다른 방식으로 처리하는 방법을 제공하고 단일 x86 기반 시스템에서 여러 운영 체제를 동시에 실행할 수있게되면 시나리오가 크게 바뀌 었습니다.

하이퍼 바이저

하이퍼 바이저는 게스트 가상 머신이 작동하는 가상 환경 작성을 처리합니다. 게스트 시스템을 감독하고 필요에 따라 리소스가 게스트에 할당되도록합니다. 하이퍼 바이저는 실제 머신과 가상 머신 사이에 있으며 가상 머신에 가상화 서비스를 제공합니다. 이를 실현하기 위해 가상 머신에서 게스트 운영 체제 조작을 인터셉트하고 호스트 머신 운영 체제에서 조작을 에뮬레이트합니다.

주로 클라우드에서 가상화 기술의 빠른 개발로 인해 Xen, VMware Player, KVM 등과 같은 하이퍼 바이저의 도움으로 단일 물리적 서버에 여러 개의 가상 서버를 만들 수있어 가상화 사용이 더욱 확대되었습니다. Intel VT 및 AMD-V와 같은 상용 프로세서에 하드웨어 지원 통합

가상화 유형

가상화 방법은 게스트 운영 체제에서 하드웨어를 모방하고 게스트 운영 환경을 에뮬레이션하는 방법에 따라 분류 할 수 있습니다. 기본적으로 가상화에는 세 가지 유형이 있습니다.

  • 에뮬레이션
  • 반 가상화
  • 컨테이너 기반 가상화

에뮬레이션

전체 가상화라고도하는 에뮬레이션은 소프트웨어에서 가상 머신 OS 커널을 완전히 실행합니다. 이 유형에 사용 된 하이퍼 바이저를 유형 2 하이퍼 바이저라고합니다. 게스트 운영 체제 커널 코드를 소프트웨어 명령으로 변환하는 호스트 운영 체제의 맨 위에 설치됩니다. 번역은 전적으로 소프트웨어로 수행되며 하드웨어가 필요하지 않습니다. 에뮬레이션을 통해 에뮬레이션되는 환경을 지원하는 수정되지 않은 운영 체제를 실행할 수 있습니다. 이 유형의 가상화의 단점은 다른 유형의 가상화에 비해 성능이 저하되는 추가 시스템 리소스 오버 헤드입니다.

에뮬레이션

이 범주의 예로는 VMware Player, VirtualBox, QEMU, Bochs, Parallels 등이 있습니다.

반 가상화

유형 1 하이퍼 바이저라고도하는 반 가상화는 하드웨어 또는 "베어 메탈 (bare-metal)"에서 직접 실행되며 가상화 서비스를 실행하는 가상 머신에 직접 가상화 서비스를 제공합니다. 운영 체제, 가상화 된 하드웨어 및 실제 하드웨어가 협업하여 최적의 성능을 달성하도록 도와줍니다. 이러한 하이퍼 바이저는 일반적으로 설치 공간이 다소 작으며 자체적으로 광범위한 리소스가 필요하지 않습니다.

이 범주의 예에는 Xen, KVM 등이 포함됩니다.

반 가상화

컨테이너 기반 가상화

운영 체제 수준 가상화라고도하는 컨테이너 기반 가상화는 단일 운영 체제 커널 내에서 여러 격리 된 실행을 가능하게합니다. 최상의 성능과 밀도를 가지며 동적 리소스 관리 기능이 있습니다. 이 유형의 가상화에서 제공하는 격리 된 가상 실행 환경을 컨테이너라고하며 추적 된 프로세스 그룹으로 볼 수 있습니다.

컨테이너 기반 가상화

컨테이너 개념은 Linux 커널 버전 2.6.24에 추가 된 네임 스페이스 기능으로 가능합니다. 컨테이너는 모든 프로세스에 ID를 추가하고 모든 시스템 호출에 새로운 액세스 제어 검사를 추가합니다. 이전의 전역 네임 스페이스의 개별 인스턴스를 만들 수 있는 clone () 시스템 호출 로 액세스 합니다.

네임 스페이스는 다양한 방법으로 사용될 수 있지만 가장 일반적인 방법은 컨테이너 외부의 객체에 대한 가시성이나 액세스 권한이없는 격리 된 컨테이너를 만드는 것입니다. 컨테이너 내에서 실행되는 프로세스는 다른 종류의 객체와 마찬가지로 다른 네임 스페이스에있는 프로세스와 기본 커널을 공유하지만 일반 Linux 시스템에서 실행중인 것으로 보입니다. 예를 들어, 네임 스페이스를 사용할 때 컨테이너 내부의 루트 사용자는 컨테이너 외부의 루트로 취급되지 않으므로 추가 보안이 추가됩니다.

컨테이너 기반 가상화를 가능하게하는 다음 주요 구성 요소 인 Linux 제어 그룹 (cgroup) 서브 시스템은 프로세스를 그룹화하고 총 자원 소비를 관리하는 데 사용됩니다. 일반적으로 컨테이너의 메모리 및 CPU 소비를 제한하는 데 사용됩니다. 컨테이너화 된 Linux 시스템에는 커널이 하나만 있고 커널은 컨테이너를 완전히 볼 수 있으므로 리소스 할당 및 스케줄링 수준은 한 가지뿐입니다.

LXC, LXD, systemd-nspawn, lmctfy, Warden, Linux-VServer, OpenVZ, Docker 등을 포함하여 Linux 컨테이너에 여러 관리 도구를 사용할 수 있습니다.

컨테이너 대 가상 머신

가상 머신과 달리 컨테이너는 운영 체제 커널을 부팅 할 필요가 없으므로 컨테이너를 1 초 이내에 만들 수 있습니다. 이 기능은 컨테이너 기반 가상화를 다른 가상화 방식보다 독특하고 바람직하게 만듭니다.

컨테이너 기반 가상화는 호스트 시스템에 오버 헤드를 거의 또는 전혀 추가하지 않기 때문에 컨테이너 기반 가상화는 거의 기본 성능을 제공합니다.

컨테이너 기반 가상화의 경우 다른 가상화와 달리 추가 소프트웨어가 필요하지 않습니다.

호스트 시스템의 모든 컨테이너는 호스트 시스템의 스케줄러를 공유하므로 추가 자원이 필요하지 않습니다.

컨테이너 상태 (Docker 또는 LXC 이미지)는 가상 머신 이미지에 비해 크기가 작으므로 컨테이너 이미지를 쉽게 배포 할 수 있습니다.

컨테이너의 리소스 관리는 cgroup을 통해 수행됩니다. Cgroup은 컨테이너가 할당 된 것보다 더 많은 리소스를 소비하도록 허용하지 않습니다. 그러나 현재 호스트 시스템의 모든 리소스는 가상 시스템에서 볼 수 있지만 사용할 수는 없습니다. 이는 컨테이너와 호스트 시스템을 동시에 실행 top하거나 실행하여 실현할 수 있습니다 htop. 모든 환경에서의 출력은 비슷하게 보입니다.

최신 정보:

Docker는 Linux 이외의 시스템에서 컨테이너를 어떻게 실행합니까?

Linux 커널에서 사용 가능한 기능으로 인해 컨테이너가 가능한 경우 Linux 이외의 시스템에서 컨테이너를 실행하는 방법에 대한 분명한 질문이 있습니다. Mac 및 Windows 용 Docker는 모두 Linux VM을 사용하여 컨테이너를 실행합니다. Docker Toolbox는 Virtual Box VM에서 컨테이너를 실행하는 데 사용됩니다. 그러나 최신 Docker는 Windows에서는 Hyper-V를 사용하고 Mac에서는 Hypervisor.framework를 사용합니다.

이제 Docker for Mac이 어떻게 컨테이너를 실행하는지 설명하겠습니다.

Mac 용 Docker는 https://github.com/moby/hyperkit 을 사용 하여 하이퍼 바이저 기능을 에뮬레이트하고 Hyperkit은 코어에서 hypervisor.framework를 사용합니다. Hypervisor.framework는 Mac의 기본 하이퍼 바이저 솔루션입니다. Hyperkit은 또한 VPNKit과 DataKit을 사용하여 각각 네임 스페이스 네트워크와 파일 시스템을 만듭니다.

Docker가 Mac에서 실행하는 Linux VM은 읽기 전용입니다. 그러나 다음을 실행하여 bash를 만들 수 있습니다.

screen ~/Library/Containers/com.docker.docker/Data/vms/0/tty.

이제이 VM의 커널 버전을 확인할 수도 있습니다.

# uname -a Linux linuxkit-025000000001 4.9.93-linuxkit-aufs #1 SMP Wed Jun 6 16:86_64 Linux.

모든 컨테이너는이 VM 내에서 실행됩니다.

hypervisor.framework에는 몇 가지 제한 사항이 있습니다. Docker는 docker0Mac에서 네트워크 인터페이스를 노출시키지 않습니다 . 따라서 호스트에서 컨테이너에 액세스 할 수 없습니다. 현재로서는 docker0VM 내부에서만 사용할 수 있습니다.

Hyper-v는 Windows의 기본 하이퍼 바이저입니다. 또한 Windows 10의 기능을 활용하여 Linux 시스템을 기본적으로 실행하려고합니다.


1
아주 좋은 포스트. 정말 고맙습니다! 내가 가지고있는 또 다른 질문은 Mac x86_64 컴퓨터에서 docker arm7v 32 비트 이미지를 빌드 할 수 있다는 것입니다. 그러나 x86_64 컴퓨터에 설치된 Ubuntu에서 동일한 이미지를 만들 수 없습니다. 언급 한 Mac 하이퍼 바이저 솔루션과 관련이 있습니까?
jiashenC

1
귀하의 답변은 "Docker가 Linux 이외의 시스템에서 컨테이너를 어떻게 실행합니까?"를 해결하는 유일한 방법입니다. 이 정보는 어디에서나 찾기가 매우 어렵습니다. "컨테이너는 VM과는 완전히 다릅니다!", 더 빠르고 가벼우 며, 비 Linux 시스템에서 컨테이너를 실행하는 유일한 방법은 VM을 스핀 업하는 것입니다.
Bogatyr

@Bogatyr IINM, 모든 컨테이너의 VM입니다.
dstromberg

147

이 게시물을 통해 VM과 LXC의 차이점을 몇 가지 살펴 보겠습니다. 먼저 정의 해 봅시다.

VM :

가상 시스템은 물리적 컴퓨팅 환경을 에뮬레이트하지만 CPU, 메모리, 하드 디스크, 네트워크 및 기타 하드웨어 리소스에 대한 요청은 가상화 계층에서 관리하여 이러한 요청을 기본 물리적 하드웨어로 변환합니다.

이 컨텍스트에서 VM은 게스트라고하며 VM은 실행되는 환경을 호스트라고합니다.

LXC :

Linux Containers (LXC)는 하나의 제어 호스트 (LXC 호스트)에서 여러 개의 격리 된 Linux 컨테이너를 실행할 수있는 운영 체제 수준 기능입니다. Linux 컨테이너는 하이퍼 바이저 viz가 필요하지 않으므로 VM에 대한 간단한 대안으로 사용됩니다. Virtualbox, KVM, Xen 등

Alan (행 아웃 시리즈의 Zach Galifianakis-)에 의해 마약을 받고 작년에 라스베가스에 가본 적이 없다면, Linux 컨테이너 기술에 대한 엄청난 관심이 집중 될 것입니다. 지난 몇 달 동안 전 세계에 붐을 일으킨 프로젝트는 다음과 같습니다. Docker는 클라우드 컴퓨팅 환경이 가상 머신 (VM)을 버리고 더 낮은 오버 헤드와 잠재적으로 더 나은 성능으로 인해 컨테이너로 대체해야한다는 반향을 불러 일으 킵니다.

그러나 가장 큰 문제는 실현 가능합니까?

ㅏ. LXC는 Linux 인스턴스에 적용됩니다. Linux의 풍미가 다를 수 있습니다 (예 : CentOS 호스트의 Ubuntu 컨테이너이지만 여전히 Linux 임). VM을 살펴보면 Windows 기반 컨테이너의 범위가 넓어지고 하이퍼 바이저는 Linux 또는 Windows 운영 체제로 제한되지 않습니다.

비. LXC는 VM에 비해 오버 헤드가 낮고 성능이 더 좋습니다. 도구 즉. LXC 기술을 기반으로 구축 된 Docker는 개발자에게 응용 프로그램을 실행할 수있는 플랫폼을 제공했으며 동시에 운영 직원에게 프로덕션 서버 또는 데이터 센터에 동일한 컨테이너를 배포 할 수있는 도구를 제공했습니다. 개발자가 응용 프로그램을 실행하고, 응용 프로그램을 부팅 및 테스트하는 개발자와 해당 응용 프로그램을 완벽하게 배포하는 운영 담당자 사이에 경험을 쌓으려고 노력합니다. 이는 모든 마찰이 존재하고 DevOps의 목적이 이러한 사일로를 분해하기 때문입니다.

따라서 가장 좋은 방법은 클라우드 인프라 공급자가 VM과 LXC의 적절한 사용을 권장해야합니다. VM과 LXC는 각각 특정 워크로드와 시나리오를 처리하는 데 적합하기 때문입니다.

VM을 포기하는 것은 현재로서는 실용적이지 않습니다. 따라서 VM과 LXC는 각자 고유 한 존재와 중요성을 가지고 있습니다.


4
위의 "b"부분은 Docker 사람들이 기술에 대해 말한 것과 정확히 같습니다. 개발 배포 작업을보다 쉽게하기위한 것입니다. 그리고 개발자로서의 경험과 sysop으로, 나는 동의해야합니다.
WineSoaked

3
꽤 추상적 인 답변입니다. Docker를 사용하거나 사용하지 않을 때는 사용 사례가 필요합니다. 그게 문제입니다. 누구나 Docker와 같은 것을 찾을 수 있지만 실제 시나리오에 대해서는 소수만 설명 할 수 있습니다.
Ivan Voroshilin

1
docker는 더 이상 LXC에 의존하지 않기 때문에 windows 세계로 옮겨지고 있습니다 : blogs.msdn.com/b/nzdev/archive/2015/06/02/… 내가 대답을 오해하면 저를 정정하십시오
bubakazouba

6
컨테이너"(예 : Centos 호스트의 Ubuntu 컨테이너이지만 여전히 Linux 임") 부분을 이해하기가 어렵습니다 . 내가 이해하는 방법은 컨테이너가 호스트 커널을 공유한다는 것입니다. 예를 들어 Linux 커널 4.6을 실행하는 호스트 VM이 있고 여러 게스트 VM에서 Linux 커널 2.4, 2.6, 3.2, 4.1 및 4.4를 실행하는 경우. 해당 커널에 특정한 명령을 실행하면 게스트 커널의 동작 (호스트가 아닌)을 얻게됩니다. 그러나 게스트 VM이 컨테이너 인 경우 실행 된 명령이 호스트 커널에 의해 결정됩니까?
Jeach

@bubakazouba 예. 당신이 올바른지. 이제 그들은 runC를 사용합니다
Rumesh Eranga Hapuarachchi

140

여기에있는 대부분의 답변은 가상 머신에 대한 것입니다. Docker를 사용하는 지난 몇 년 동안 가장 도움이 된이 질문에 대한 한 줄짜리 응답을 제공 할 것입니다. 이것입니다 :

Docker는 가상 머신이 아닌 프로세스를 실행하는 멋진 방법입니다.

이제 그 의미에 대해 좀 더 설명하겠습니다. 가상 머신은 자신의 짐승입니다. Docker가 무엇인지 설명하고 싶습니다. 당신이 더 많은 가상 머신이 무엇인지 설명하는 것보다 이해하는 데 도움이됩니다. 특히 여기에 누군가가 "가상 머신"이라고 할 때의 의미를 정확하게 알려주는 많은 훌륭한 답변이 있기 때문입니다. 그래서...

Docker 컨테이너는 프로세스 (및 그 자식) 일 뿐이며 나머지 프로세스에서 호스트 시스템 커널 내부의 cgroup을 사용하여 구획화 됩니다. 실제로 ps aux호스트에서 실행하여 Docker 컨테이너 프로세스를 볼 수 있습니다 . 예를 들어, apache2"컨테이너에서"시작 apache2은 호스트에서 특수 프로세스로 시작 됩니다. 컴퓨터의 다른 프로세스에서 구획화되었습니다. 컨테이너는 컨테이너화 된 프로세스 수명 밖에서는 존재하지 않습니다. 프로세스가 죽으면 컨테이너가 죽습니다. Docker가 pid 1컨테이너 내부를 응용 프로그램으로 대체하기 때문 pid 1입니다 (일반적으로 init 시스템입니다). 마지막 요점 pid 1은 매우 중요합니다.

각 컨테이너 프로세스에서 사용하는 파일 시스템에 이르기까지 Docker는 UnionFS 지원 이미지를 사용합니다. 이 이미지는 다운로드 할 때 다운로드하는 이미지 docker pull ubuntu입니다. 각 "이미지"는 일련의 레이어 및 관련 메타 데이터입니다. 레이어링의 개념은 여기서 매우 중요합니다. 각 레이어는 그 아래 레이어에서 변경된 것입니다. 예를 들어 Docker 컨테이너를 빌드하는 동안 Dockerfile에서 파일을 삭제하면 실제로는 마지막 레이어 위에 "이 파일이 삭제되었습니다"라는 레이어가 생성됩니다. 또한 파일 시스템에서 큰 파일을 삭제할 수는 있지만 이미지는 여전히 같은 양의 디스크 공간을 차지합니다. 파일은 여전히 ​​현재 레이어 아래에 있습니다. 레이어 자체는 단지 파일의 tarball입니다. 당신은 이것을 테스트 할 수 있습니다docker save --output /tmp/ubuntu.tar ubuntu다음 cd /tmp && tar xvf ubuntu.tar. 그런 다음 둘러 볼 수 있습니다. 긴 해시처럼 보이는 모든 디렉토리는 실제로 개별 레이어입니다. 각 파일에는 파일 ( layer.tar)과 메타 데이터 (json)를 해당 특정 레이어에 대한 정보와 함께 제공합니다. 이러한 레이어는 파일 시스템의 변경 사항을 설명하며 원래 상태의 "맨 위에"레이어로 저장됩니다. "현재"데이터를 읽을 때 파일 시스템은 최상위 계층의 변경 사항 만보고있는 것처럼 데이터를 읽습니다. 파일 시스템이 최상위 계층 만보고 있기 때문에 파일이 여전히 "이전"계층에 존재하더라도 파일이 삭제 된 것처럼 보입니다. 이렇게하면 각 컨테이너에서 최상위 계층의 파일 시스템에 약간의 변경이 있었더라도 완전히 다른 컨테이너가 파일 시스템 계층을 공유 할 수 있습니다. 컨테이너가 기본 이미지 레이어를 공유 할 때 많은 디스크 공간을 절약 할 수 있습니다. 하나,

Docker의 네트워킹은 이더넷 브리지 ( docker0 호스트에서 )와 호스트의 모든 컨테이너에 대한 가상 인터페이스를 . docker0컨테이너가 서로 "통신"할 수 있도록 가상 서브넷을 만듭니다 . 여기에는 컨테이너에 대한 사용자 지정 서브넷 생성 및 컨테이너가 직접 액세스 할 수 있도록 호스트의 네트워킹 스택을 "공유"하는 기능을 포함하여 네트워킹에 대한 많은 옵션이 있습니다.

Docker는 매우 빠르게 움직이고 있습니다. 그 문서 는 내가 본 최고의 문서 중 일부입니다. 일반적으로 잘 작성되고 간결하며 정확합니다. 자세한 내용은 사용 가능한 설명서를 확인하고 Stack Overflow를 포함하여 온라인에서 읽은 내용에 대한 설명서를 신뢰하는 것이 좋습니다. 구체적인 질문이 있으시면 #dockerFreenode IRC에 가입 하여 문의하는 것이 좋습니다 (Freenode의 웹 채팅 을 사용해도됩니다 ).


12
"Docker는 가상 머신이 아닌 프로세스를 실행하는 멋진 방법입니다." 이것은 훌륭한 요약입니다, 감사합니다!
mkorman

감사! 이에 대한 크레딧은 #dockerFreenode IRC 의 채널에서 programmerq로 전달됩니다 .
L0j1k

이것은 다른 답변보다 훨씬 명확합니다. 나는 그것이 나를 위해 프로세스 비유라고 생각합니다. 추상화 수준을 낮 춥니 다.
Mate Mrše

"Docker는 가상 머신이 아닌 격리되고 보호되고 캡슐화 된 방식으로 프로세스를 실행하는 멋진 방법입니다." 호스트 시스템에는 서브 시스템에 대한 가시성 (프로세스 및 자원에 대한)이 있지만 분리 된 시스템에는 호스트 시스템에있는 가시성 (프로세스 및 자원에 대한)이 없습니다.
Sohail Si

87

Docker는 모든 종속성으로 응용 프로그램을 캡슐화합니다.

가상화는 베어 메탈 머신에서 일반적으로 실행할 수있는 모든 애플리케이션을 실행할 수있는 OS를 캡슐화합니다.


1
나는 LXC에 대해 배우고 있는데, 틀렸다면 정정하지만 일종의 virtualenv 일 수 있습니까? 그러나 분명히 말하기 위해 파이썬으로
포경 된

2
이 답변이 가장 좋습니다. 간단하고 바로갑니다. 이제 LXC와 Virtualizer가 무엇을 할 수 있는지에 대한 기본 지식을 갖추 었으므로 다른 읽기의 세부 정보가 의미가 있습니다.
Phil

2
@ 필 먼저 위의 자세한 답변을 읽은 후에했습니다.
johnny

캡슐화 방법을 알고 싶다고 가정합니다. 그것은 그들 사이의 차이점을 보여주는 큰 부분이지만 대답하지 않았습니다.
빛 G.

60

둘 다 매우 다릅니다. Docker는 가볍고 LXC / libcontainer (커널 이름 간격 및 cgroup에 의존)를 사용하며 하이퍼 바이저, KVM과 같은 시스템 / 하드웨어 에뮬레이션이 없습니다. 무거운 젠.

Docker 및 LXC는 샌드 박싱, 컨테이너화 및 리소스 격리에 더 적합합니다. IPC, NS (마운트), 네트워크, PID, UTS 등에 네임 스페이스를 제공하는 호스트 OS (현재 Linux 커널 만 해당) 클론 API를 사용합니다.

메모리, I / O, CPU 등은 어떻습니까? 특정 리소스 (CPU, 메모리 등) 사양 / 제한이있는 그룹을 생성하고 프로세스를 거기에 넣을 수있는 cgroup을 사용하여 제어됩니다. Docker는 LXC 외에도 스토리지 백엔드 ( http://www.projectatomic.io/docs/filesystems/ )를 제공합니다. 예를 들어, 다른 마운트 네임 스페이스간에 레이어를 추가하고 공유 할 수있는 통합 마운트 파일 시스템입니다.

이것은 기본 이미지가 일반적으로 읽기 전용이며 컨테이너가 레이어에서 무언가를 수정할 때만 읽기-쓰기 파티션 (일명 복사시 복사)에 무언가를 쓸 수있는 강력한 기능입니다. 또한 레지스트리 및 이미지 버전 관리와 같은 다른 많은 래퍼도 제공합니다.

일반적인 LXC를 사용하면 일부 rootfs와 함께 제공되거나 rootfs를 공유하고 공유 할 때 변경 사항이 다른 컨테이너에 반영됩니다. 이러한 추가 기능으로 인해 Docker는 LXC보다 인기가 있습니다. LXC는 네트워크 및 UI와 같은 외부 엔터티에 노출 된 프로세스에 대한 보안을 구현하기 위해 임베디드 환경에서 널리 사용됩니다. Docker는 일관된 프로덕션 환경이 필요한 클라우드 다중 테넌시 환경에서 널리 사용됩니다.

일반적인 VM (예 : VirtualBox 및 VMware)은 하이퍼 바이저를 사용하며 관련 기술에는 첫 번째 OS (호스트 OS 또는 게스트 OS 0)의 첫 번째 계층이되는 전용 펌웨어 또는 호스트 OS에서 실행되는 소프트웨어가 있습니다. CPU, USB / 액세서리, 메모리, 네트워크 등과 같은 하드웨어 에뮬레이션을 게스트 OS에 제공합니다. VM은 여전히 ​​높은 보안 다중 테넌트 환경에서 인기가 있습니다 (2015 년 기준).

Docker / LXC는 저렴한 하드웨어에서 거의 실행될 수 있습니다 (최신 커널이있는 한 1GB 미만의 메모리도 괜찮습니다) 대 일반 VM은 2GB 이상의 메모리가 필요합니다. . 그러나 Windows, Linux 및 Mac에서 VM 유형을 실행할 수있는 Windows (2014 년 11 월 기준)와 같은 OS에서는 호스트 OS에 대한 Docker 지원을 사용할 수 없습니다.

다음은 docker / rightscale의 사진입니다. 여기 오른쪽 스케일의 그림이 있습니다.


34

1. 경량

이것은 아마도 많은 도커 학습자들에게 첫 인상입니다.

첫째, 도커 이미지는 일반적으로 VM 이미지보다 작으므로 쉽게 빌드, 복사, 공유 할 수 있습니다.

둘째, Docker 컨테이너는 몇 밀리 초 안에 시작할 수 있지만 VM은 몇 초 안에 시작됩니다.

2. 계층 파일 시스템

이것은 Docker의 또 다른 주요 기능입니다. 이미지에는 레이어가 있으며 다른 이미지는 레이어를 공유 할 수있어 공간을 절약하고 더 빠르게 만들 수 있습니다.

모든 컨테이너가 Ubuntu를 기본 이미지로 사용하는 경우 모든 이미지에 고유 한 파일 시스템이있는 것은 아니지만 동일한 밑줄 우분투 파일을 공유하며 자체 응용 프로그램 데이터 만 다릅니다.

3. 공유 OS 커널

컨테이너를 프로세스로 생각하십시오!

호스트에서 실행되는 모든 컨테이너는 실제로 다른 파일 시스템을 가진 많은 프로세스입니다. 이들은 동일한 OS 커널을 공유하며 시스템 라이브러리 및 종속성 만 캡슐화합니다.

이것은 여분의 OS 커널을 유지하지 않는 대부분의 경우에 좋지만 컨테이너간에 엄격한 격리가 필요한 경우 문제가 될 수 있습니다.

왜 중요한가요?

이 모든 것이 혁명이 아닌 개선 된 것처럼 보입니다. 음, 양적 축적은 질적 변환으로 이어집니다 .

응용 프로그램 배포에 대해 생각해보십시오. 새 소프트웨어 (서비스)를 배포하거나 업그레이드하려면 새 VM을 만드는 대신 구성 파일과 프로세스를 변경하는 것이 좋습니다. 업데이트 된 서비스로 VM을 생성하므로 테스트 (데브와 QA 간 공유)로 프로덕션 환경에 배포하는 데 몇 시간, 심지어 며칠이 걸립니다. 문제가 발생하면 다시 시작하여 더 많은 시간을 낭비해야합니다. 따라서 구성 관리 도구 (인형, saltstack, chef 등)를 사용하여 새 소프트웨어를 설치하고 새 파일을 다운로드하는 것이 좋습니다.

도커와 관련하여 새로 만든 도커 컨테이너를 사용하여 이전 컨테이너를 교체하는 것은 불가능합니다. 유지 관리가 훨씬 쉬워집니다! 새로운 이미지를 구축하고 QA와 공유하고 테스트하고 몇 분 (모든 것이 자동화 된 경우)에 배치하면 최악의 경우 몇 시간이 걸립니다. 이를 불변 인프라 라고합니다 . 소프트웨어를 유지 (업그레이드)하지 말고 새 소프트웨어를 만드십시오.

서비스 제공 방식을 변화시킵니다. 우리는 응용 프로그램을 원하지만 VM을 유지 관리해야합니다 (이는 고통스럽고 응용 프로그램과 거의 관련이 없음). Docker는 응용 프로그램에 집중하고 모든 것을 원활하게합니다.


27

Docker, 기본적으로 컨테이너는 OS 가상화를 지원합니다. 즉, 응용 프로그램 은 OS 의 완전한 인스턴스가 있다고 생각하는 반면 VM은 하드웨어 가상화를 지원 합니다 . OS를 부팅 할 수있는 실제 머신 인 것 같습니다.

Docker에서 실행되는 컨테이너는 호스트 OS 커널을 공유하는 반면 VM에서는 자체 OS 파일이 있습니다. 응용 프로그램을 개발하는 환경 (OS)은 응용 프로그램을 "테스트"또는 "제작"과 같은 다양한 서비스 환경에 배포 할 때 동일합니다.

예를 들어, 포트 4000에서 실행되는 웹 서버를 개발하는 경우 "테스트"환경에 배포하면 해당 포트가 이미 다른 프로그램에서 사용되므로 작동이 중지됩니다. 컨테이너에는 레이어가 있습니다. OS에 대한 모든 변경 사항은 하나 이상의 레이어에 저장되며 해당 레이어는 이미지의 일부가되므로 이미지가있는 곳마다 종속성이 나타납니다.

아래에 표시된 예에서 호스트 시스템에는 3 개의 VM이 있습니다. VM에서 완전한 격리를 제공하기 위해 각각 OS의 전체 메모리 인스턴스와 함께 자체 OS 파일, 라이브러리 및 응용 프로그램 코드 사본이 있습니다.컨테이너없이 아래 그림은 컨테이너와 동일한 시나리오를 보여줍니다. 여기서 컨테이너는 커널과 라이브러리를 포함하여 호스트 운영 체제를 공유하기 때문에 OS를 부팅하거나 라이브러리를로드하거나 해당 파일의 개인 메모리 비용을 지불 할 필요가 없습니다. 이들이 차지하는 유일한 증분 공간은 응용 프로그램을 컨테이너에서 실행하는 데 필요한 메모리 및 디스크 공간입니다. 응용 프로그램 환경은 전용 OS처럼 느껴지지만 응용 프로그램은 전용 호스트에있는 것처럼 배포됩니다. 컨테이너화 된 응용 프로그램은 몇 초 만에 시작되며 VM의 경우보다 더 많은 응용 프로그램 인스턴스가 시스템에 적합 할 수 있습니다. 여기에 이미지 설명을 입력하십시오

출처 : https://azure.microsoft.com/en-us/blog/containers-docker-windows-and-trends/


나는 첫 번째 단락을 매우 좋아합니다.
빛 G.

23

응용 프로그램을 실행할 스택을 제공하는 세 가지 설정이 있습니다 (컨테이너가 무엇인지, 컨테이너가 다른 솔루션보다 훨씬 강력하다는 것을 인식하는 데 도움이 됨).

1) Traditional Servers(bare metal)
2) Virtual machines (VMs)
3) Containers

1) 기존 서버 스택은 운영 체제와 응용 프로그램을 실행하는 실제 서버로 구성됩니다.

장점 :

  • 원자재 활용

  • 격리

단점 :

  • 매우 느린 배포 시간
  • 비싼
  • 낭비 된 자원
  • 확장하기 어려움
  • 마이그레이션하기 어려움
  • 복잡한 구성

2) VM 스택 은 운영 체제를 실행하는 물리적 서버와 가상 시스템, 공유 리소스 및 네트워킹 인터페이스를 관리하는 하이퍼 바이저로 구성됩니다. 각 Vm은 게스트 운영 체제, 응용 프로그램 또는 응용 프로그램 집합을 실행합니다.

장점 :

  • 좋은 자원 사용
  • 손쉬운 확장
  • 간편한 백업 및 마이그레이션
  • 비용 효율성
  • 적응성

단점 :

  • 리소스 할당에 문제가 있습니다
  • 공급 업체 잠금
  • 복잡한 구성

3) 컨테이너 설정 은 다른 스택과의 주요 차이점은 컨테이너 기반 가상화는 호스트 OS의 커널을 사용하여 여러 개의 격리 된 게스트 인스턴스를 럼주로 만드는 것입니다. 이러한 게스트 인스턴스를 컨테이너라고합니다. 호스트는 물리적 서버 또는 VM 일 수 있습니다.

장점 :

  • 격리
  • 경량
  • 효과적인 자원
  • 쉽게 마이그레이션
  • 보안
  • 낮은 오버 헤드
  • 미러 생산 및 개발 환경

단점 :

  • 동일한 아키텍처
  • 리소스가 많은 앱
  • 네트워킹 및 보안 문제.

컨테이너 설정과 이전 설정을 비교하면 컨테이너화가 현재까지 알려진 가장 빠르고 가장 효율적이며 가장 효과적인 설정이라고 결론을 내릴 수 있습니다. 컨테이너는 응용 프로그램을 실행하는 격리 된 인스턴스입니다. 도커는 컨테이너를 어떤 식 으로든 가동시킵니다. 레이어는 몇 초 안에 실행되는 기본 스토리지 드라이버 (오버레이 드라이버)와 컨테이너에 커밋 한 후 쓰기 위의 복사 레이어로 런타임 메모리를 얻습니다. 용기.VM의 경우 모든 것을 가상화 환경에로드하는 데 약 1 분이 걸립니다. 이 경량 인스턴스는 쉽게 교체, 재 구축 및 이동할 수 있습니다. 이를 통해 프로덕션 및 개발 환경을 미러링 할 수 있으며 CI / CD 프로세스에 큰 도움이됩니다. 컨테이너가 제공 할 수있는 장점은 매우 매력적입니다.


VM과 비교하여 이것이 "가장 안전한 설정"인 이유를 알려주십시오.
MKesper

@MKesper : 레거시 환경에서 컨테이너 환경으로 마이그레이션 할 때 침입 방지를위한 사전 대응 방식이 아닌 사전 대응 방식을 기반으로하는 보안 패러다임을 구축하는 다양한 방법이 있습니다. 보다 세밀하고 미묘한 수준으로 응용 프로그램 및 런타임을 보호 할 수 있습니다. 또한 워크 플로를 방해하기 전에 잠재적 인 보안 위협을 식별하고 해결할 수 있습니다. 또한 정적 분석을 ML과 결합하여 런타임 방어를 자동화하고 환경 전체에 정책을 시행 할 수 있습니다. 따라서 "가장 안전한 설정"라인입니다.
mohan08p

18

다음과 관련하여 :-

"일관된 프로덕션 환경에 단순히 배포하는 것보다 소프트웨어를 Docker 이미지에 쉽게 배포하는 이유는 무엇입니까?"

대부분의 소프트웨어는 여러 환경에 배포되며 일반적으로 다음 중 3 가지 이상입니다.

  1. 개별 개발자 PC
  2. 공유 개발자 환경
  3. 개별 테스터 PC
  4. 공유 테스트 환경
  5. 품질 관리 환경
  6. UAT 환경
  7. 부하 / 성능 테스트
  8. 라이브 스테이징
  9. 생산
  10. 보관

고려해야 할 다음과 같은 요소도 있습니다.

  • 개발자와 실제로 테스터는 작업의 본질에 따라 미묘하거나 전혀 다른 PC 구성을 갖습니다.
  • 개발자는 종종 회사 또는 비즈니스 표준화 규칙 (예 : 자신의 컴퓨터에서 원격으로 개발하는 프리랜서) 또는 PC를 특정 '구성'하기 위해 '고용'또는 '계약'하지 않은 오픈 소스 프로젝트에 기여한 프리랜서가 통제 할 수없는 PC에서 개발할 수 있습니다. 방법)
  • 일부 환경은로드 밸런싱 구성에서 고정 된 수의 여러 시스템으로 구성됩니다.
  • 많은 프로덕션 환경에는 트래픽 수준에 따라 클라우드 기반 서버가 동적으로 (또는 '탄력적으로') 생성 및 파괴됩니다

보시다시피, 조직에 대한 추정 된 총 서버 수는 거의 단일 수치가 아니며, 거의 3 배이며, 여전히 훨씬 더 높을 수 있습니다.

이 처음부터 일관성있는 환경을 조성하는 것은 단지 때문에 엄청난 양의 (심지어 그린 필드 시나리오)의 열심히는하지만 모든 수단 들을 일관성을 유지하는 것은 거의 불가능 동적 (새 서버 추가 서버의 높은 번호, 제공 또는 수동), o / s 공급 업체, 안티 바이러스 공급 업체, 브라우저 공급 업체 등의 자동 업데이트, 개발자 또는 서버 기술자가 수행 한 수동 소프트웨어 설치 또는 구성 변경 등을 반복하겠습니다. 사실상 불가능합니다. 환경을 일관되게 유지하기 위해 (순수한 자에게는 할 수 있지만 많은 시간과 노력과 훈련이 필요하기 때문에 VM과 컨테이너 (예 : Docker)가 처음에 고안된 이유입니다).

따라서 "모든 환경의 일관성을 유지하기가 매우 어려워지고 학습 곡선을 고려할 때에도 도커 이미지에 소프트웨어를 쉽게 배포 할 수 있습니까?" 와 같은 질문을 생각해보십시오. . 나는 당신이 대답이 항상 "예"라고 생각할 것이라고 생각합니다. 그러나 알아낼 수있는 유일한 방법은 스택 오버플로에 새로운 질문을 게시하는 것입니다.


따라서 모든 OS / 버전 조합이있는 15 개의 다른 상자로 도커 이미지를 배포하면 모든 도커 이미지가 동일하게 실행됩니까?
Teoman shipahi

@Teomanshipahi이 모든 컨테이너가 호스트가 제공 한 동일한 커널을 사용할 수 있다면, 모두 성공적으로 실행됩니다.
빛 G.

로컬에서 windows 용 docker를 사용하는 경우 linux / mac에서 동일한 방식으로 배포하고 실행할 수 있습니까?
Teoman shipahi

항상 빛을 발하는 것들은 여전히 ​​버전 의존성이 있다는 것입니다. 1) 개발자는 이미지에 포함 된 것과 동일한 환경에서 개발해야합니다. 2) 개발 환경과 테스트 환경은 리눅스 커널과 도커 자체의 동일한 (또는 호환되는) 버전을 실행해야합니다 ... 예?
Bogatyr

18

차이점에 대해 더 자세히 설명하는 많은 답변이 있지만 여기에 간단한 설명이 있습니다.

한 가지 중요한 차이점은 VM이 별도의 커널을 사용하여 OS를 실행한다는 것 입니다. 그것이 무겁고 부팅하는데 시간이 걸리고 더 많은 시스템 리소스를 소비하는 이유입니다.

Docker에서 컨테이너는 커널 을 호스트와 공유합니다 . 따라서 가볍고 빠르게 시작하고 멈출 수 있습니다.

가상화에서 리소스는 설정 시작시 할당되므로 많은 시간 동안 가상 머신이 유휴 상태 일 때 리소스가 완전히 활용되지 않습니다. Docker에서 컨테이너에는 고정 된 양의 하드웨어 리소스가 할당되지 않으며 요구 사항에 따라 리소스를 자유롭게 사용할 수 있으므로 확장 성이 뛰어납니다.

Docker는 UNION File system을 사용 합니다 . Docker는 copy-on-write 기술을 사용하여 컨테이너가 사용하는 메모리 공간을 줄입니다. 자세한 내용은 여기를 참조하십시오


1
"가상화에서 리소스는 설정 시작시 할당되므로 여러 시간 동안 가상 시스템이 유휴 상태 일 때 리소스가 완전히 활용되지 않습니다."Hyper-V에는 동적 메모리 개념이 있으며 최소, 최대를 지정할 수 있습니다. 및 시동 RAM.
Mariusz

15

가상 머신을 사용하면 서버가 있고 해당 서버에 호스트 운영 체제가 있고 하이퍼 바이저가 있습니다. 그런 다음 해당 하이퍼 바이저 위에서 실행하면 해당 서버에 응용 프로그램 및 종속 바이너리와 라이브러리가있는 게스트 운영 체제가 얼마든지 있습니다. 게스트 운영 체제 전체를 제공합니다. 꽤 무겁습니다. 또한 각 물리적 시스템에 실제로 얼마나 많이 넣을 수 있는지에 대한 제한이 있습니다.

여기에 이미지 설명을 입력하십시오

반면 Docker 컨테이너 는 약간 다릅니다. 서버가 있습니다. 호스트 운영 체제가 있습니다. 그러나 대신에 하이퍼 바이저 , 우리는이 도커 엔진 이 경우,. 이 경우 전체 게스트 운영 체제를 제공하지 않습니다.우리는 운영 체제의 매우 얇은 계층을 가져오고 있으며 컨테이너는 커널 기능을 얻기 위해 호스트 OS와 통신 할 수 있습니다. 그리고 우리는 매우 가벼운 컨테이너를 가질 수 있습니다.

응용 프로그램 코드와 필요한 이진 및 라이브러리 만 있으면됩니다. 이 바이너리와 라이브러리는 원하는 경우 다른 컨테이너에서 실제로 공유 할 수 있습니다. 그리고 이것이 우리를 가능하게하는 것은 많은 것들입니다. 시작 시간훨씬 빠릅니다 . 몇 초 안에 단일 VM을 견딜 수 없습니다. 똑같이, 그것들을 빨리 줄이십시오. 그래서 우리는 매우 빠르게 확장 및 축소 할 수 있습니다.

여기에 이미지 설명을 입력하십시오

모든 컨테이너는 자체 운영 체제 복사본에서 실행되고 있다고 생각합니다. 자체 파일 시스템, 자체 레지스트리 등이 있습니다. 일종의 거짓말입니다. 실제로 가상화되고 있습니다.



11

프로덕션 환경에서 Docker를 사용하고 준비했습니다. 익숙해지면 멀티 컨테이너 및 격리 된 환경을 구축하는 데 매우 강력합니다.

Docker는 LXC (Linux Container)를 기반으로 개발되었으며 많은 Linux 배포판, 특히 Ubuntu에서 완벽하게 작동합니다.

Docker 컨테이너는 격리 된 환경입니다. topDocker 이미지에서 생성 된 Docker 컨테이너에서 명령 을 실행할 때 확인할 수 있습니다 .

또한 dockerFile 구성 덕분에 매우 가볍고 유연합니다.

예를 들어 Docker 이미지를 만들고 DockerFile을 구성하고 예를 들어 실행 중일 때 wthis 'this', apt-get 'that', 'some shell script'실행, 환경 변수 설정 등을 알 수 있습니다.

마이크로 서비스 프로젝트 및 아키텍처에서 Docker는 매우 실행 가능한 자산입니다. Docker, Docker swarm, Kubernetes 및 Docker Compose로 확장 성, 탄력성 및 탄력성을 얻을 수 있습니다.

Docker와 관련된 또 다른 중요한 문제는 Docker Hub 및 해당 커뮤니티입니다. 예를 들어 Prometheus, Grafana, Prometheus-JMX-Exporter 및 Docker를 사용하여 kafka를 모니터링하기위한 에코 시스템을 구현했습니다.

이를 위해 zookeeper, kafka, Prometheus, Grafana 및 jmx-collector에 대해 구성된 Docker 컨테이너를 다운로드 한 다음 YAML 파일을 사용하여 일부 구성 요소를 마운트하거나 Docker 컨테이너에서 일부 파일 및 구성을 변경했습니다. 단일 아키텍처에서 다중 컨테이너 Docker를 사용하여이 아키텍처를 여러 서버로 쉽게 이동할 수있는 격리 및 확장 성 및 복원력을 갖춘 kafka 모니터링을위한 전체 시스템을 구축합니다.

Docker Hub 사이트 외에도 quay.io라는 또 다른 사이트가 있습니다.이 사이트에는 자체 Docker 이미지 대시 보드를 가져 와서 가져 오거나 푸시 할 수 있습니다. Docker Hub에서 Docker 이미지를 quay로 가져 와서 자신의 컴퓨터에서 quay에서 실행할 수도 있습니다.

참고 : 처음에는 학습 독 커가 복잡하고 어려워 보이지만 익숙해지면 학습 독 퍼가 없으면 일할 수 없습니다.

잘못된 명령을 실행하거나 컨테이너와 모든 데이터 및 구성을 실수로 제거했을 때 Docker로 작업 한 첫 날을 기억합니다.


6

Docker 가 자체적으로 소개 하는 방법은 다음과 같습니다.

Docker는 컨테이너 이동을 주도하는 회사이며 하이브리드 클라우드 전체의 모든 애플리케이션을 처리 할 수있는 유일한 컨테이너 플랫폼 제공 업체입니다. 오늘날의 비즈니스는 디지털 혁신에 대한 압력을 받고 있지만 기존 애플리케이션 및 인프라에 의해 제약을받는 동시에 점점 더 다양한 클라우드, 데이터 센터 및 애플리케이션 아키텍처 포트폴리오를 합리화합니다. Docker는 응용 프로그램과 인프라, 개발자 및 IT 운영 부서 간의 진정한 독립성을 통해 잠재력을 발휘하고 더 나은 협업 및 혁신을위한 모델을 만듭니다.

따라서 Docker 는 컨테이너 기반이므로 현재 컴퓨터에서 실행할 수있는 이미지와 컨테이너가 있습니다. VM 과 같은 운영 체제는 포함하지 않지만 Java, Tomcat 등과 같은 다른 작업 팩 팩과 같습니다.

컨테이너를 이해하면 Docker가 무엇인지, VM 과 어떻게 다른지 알 수 있습니다 ...

컨테이너 란 무엇입니까?

컨테이너 이미지는 코드, 런타임, 시스템 도구, 시스템 라이브러리, 설정 등 실행에 필요한 모든 것을 포함하는 경량의 독립형 실행 가능 소프트웨어 패키지입니다. Linux 및 Windows 기반 앱 모두에서 사용할 수있는 컨테이너화 된 소프트웨어는 환경에 관계없이 항상 동일하게 실행됩니다. 컨테이너는 개발 환경과 준비 환경의 차이와 같이 주변 환경에서 소프트웨어를 격리하고 동일한 인프라에서 다른 소프트웨어를 실행하는 팀 간의 충돌을 줄입니다.

도커

아래 이미지에서 볼 수 있듯이 각 컨테이너에는 별도의 팩이 있으며 시스템 운영 체제와 동일한 단일 시스템 공유에서 실행됩니다.


4

여기에는 Docker의 기원뿐만 아니라 VM과 컨테이너의 차이점을 명확하게 설명하는 멋진 기술 답변이 많이 있습니다.

저에게 VM과 Docker의 근본적인 차이점은 애플리케이션 프로모션을 관리하는 방법입니다.

VM을 사용하면 응용 프로그램 및 해당 종속성을 한 VM에서 다음 DEV로, UAT에서 PRD로 승격시킬 수 있습니다.

  1. 종종 이러한 VM에는 다른 패치와 라이브러리가 있습니다.
  2. 여러 응용 프로그램이 VM을 공유하는 것은 드문 일이 아닙니다. 이를 위해서는 모든 응용 프로그램의 구성 및 종속성 관리가 필요합니다.
  3. 백 아웃을하려면 VM에서 변경 사항을 취소해야합니다. 또는 가능하면 복원하십시오.

Docker를 사용하면 응용 프로그램을 필요한 컨테이너와 함께 자체 컨테이너 안에 묶은 다음 전체 컨테이너를 단일 단위로 승격시킬 수 있습니다.

  1. 커널을 제외하고 패치와 라이브러리는 동일합니다.
  2. 일반적으로 컨테이너 당 하나의 응용 프로그램 만 있으므로 구성이 간단합니다.
  3. 제거는 컨테이너 중지 및 삭제로 구성됩니다.

따라서 VM을 사용하는 가장 기본적인 수준에서는 응용 프로그램 및 해당 종속성을 개별 구성 요소로 홍보하는 반면 Docker를 사용하면 모든 것을 한 번에 홍보 할 수 있습니다.

Kubernetes 또는 Docker Swarm과 같은 도구가 작업을 크게 단순화하지만 컨테이너 관리와 관련된 문제가 있습니다.

당사 사이트를 사용함과 동시에 당사의 쿠키 정책개인정보 보호정책을 읽고 이해하였음을 인정하는 것으로 간주합니다.
Licensed under cc by-sa 3.0 with attribution required.