我应该使用Vagrent还是Docker来创建一个隔离的环境?

我使用Ubuntu进行开发和部署,并且需要创建一个隔离的环境。

为此,我正在考虑Vagrent或Docker。优点和缺点是什么,或者这些解决方案如何比较?

418286 次浏览

如果你的目的是隔离,我认为Docker是你想要的。

Vagrent是一个虚拟机管理器。它允许您编写虚拟机配置和配置脚本。然而,它仍然是一个依赖于VirtualBox(或其他)的虚拟机,开销巨大。它需要你有一个巨大的硬盘文件,它需要大量的内存,性能可能不是很好。

另一方面,Docker通过LXC使用内核cgroup和命名空间。这意味着您使用与主机相同的内核和相同的文件系统。您可以将Dockerfile与docker build命令一起使用,以处理容器的配置和配置。您在docs.docker.com中有一个关于如何制作Dockerfile的示例;它非常直观。

你想使用Vagrent的唯一原因是如果你需要在你的Ubuntu机器上进行BSD、Windows或其他非Linux开发。否则,去Docker。

在回答之前,我承认我没有使用Docker的经验,除了作为一个狂热的观察者,这个看起来非常整洁的解决方案正在获得很大的吸引力。

我确实有相当多的Vagrent经验,可以强烈推荐它。就基于虚拟机而不是基于LXC而言,这无疑是一个更重量级的解决方案。然而,我发现一台不错的笔记本电脑(8 GB RAM,i5/i7 CPU)使用Vag犯人/VirtualBox以及开发工具运行虚拟机没有问题。

Vagrent真正伟大的事情之一是与木偶/厨师/shell脚本集成以实现自动配置。如果您使用这些选项之一来配置您的正式生产环境,您可以创建一个与您将要获得的几乎相同的开发环境,这正是您想要的。

Vagrent的另一个好处是,您可以将Vagrantfile与应用程序代码一起版本化。这意味着您团队中的其他人都可以共享此文件,并且您可以保证每个人都使用相同的环境配置。

有趣的是,Vagrent和Docker实际上可能是互补的。Vagrent可以扩展以支持不同的虚拟化提供商,Docker可能是在不久的将来获得支持的此类提供商之一。有关该主题的最近讨论,请参阅https://github.com/dotcloud/docker/issues/404

流浪汉-lxc是Vagrent的插件,可让您使用LXC来预配Vag犯人。它不具备默认的Vagrent VM(VirtualBox)所具有的所有功能,但它应该比docker容器更具灵活性。链接中有一个视频展示了它的功能,值得一看。

免责声明:我写了Vagrent!但因为我写了Vagrent,我大部分时间都生活在运营模式中,其中包括Docker等软件。我与许多使用Vagrent的公司合作,许多公司使用Docker,我看到了两者是如何相互作用的。

在我说得太多之前,直接回答:在你的特定场景中(你自己单独工作、Linux工作、在生产中使用Docker),你可以单独使用Docker并简化事情。在许多其他场景中(我将进一步讨论),这并不容易。

直接将Vagrent和Docker进行比较是不正确的,在某些情况下,它们确实有重叠,在绝大多数情况下,它们没有重叠。实际上,更合适的比较是Vagrent和Boot2Docker(可以运行Docker的最小操作系统)这样的比较。从抽象的角度来看,Vag犯人比Docker高了一个层次,所以在大多数情况下,这不是一个公平的比较。

Vagrent启动运行应用程序/服务以进行开发。这可以在VirtualBox上,威睿。它可以像AWS、OpenStack一样远程。在这些中,如果你使用容器,Vag犯人不在乎,并拥抱这一点:例如,它可以自动安装、下拉、构建和运行Docker容器。在Vag犯人1.6中,Vag犯人有基于docker的开发环境,并支持在Linux、Mac和Windows上使用与Vag犯人相同的工作流程的Docker。Vag犯人并不试图在这里取代Docker,它拥抱Docker实践。

Docker专门运行Docker容器。如果你直接与Vagrent进行比较:它是一个更具体(只能运行Docker容器)、不太灵活(需要Linux或Linux主机)的解决方案。当然,如果你谈论的是生产或CI,那就无法与Vagrent相提并论!

如果您的组织只为所有项目运行Docker容器,并且只有开发人员在Linux上运行,那么好吧,Docker绝对适合您!

否则,我看不出尝试单独使用Docker有什么好处,因为你失去了很多Vagrent提供的东西,这些东西具有真正的业务/生产力优势:

  • Vagrent可以启动VirtualBox、威睿、AWS、OpenStack等机器。无论您需要什么,Vagrent都可以启动它。如果您使用Docker,Vag犯人可以在任何这些机器上安装Docker,以便您可以将它们用于该目的。

  • Vagrent是适用于所有项目的单一工作流。或者换句话说,这只是人们运行一个项目无论是否在Docker容器中都必须学习的一件事。例如,如果将来有竞争对手出现来直接与Docker竞争,Vag犯人也将能够运行它。

  • Vagrent适用于Windows(回到XP)、Mac(回到10.5)和Linux(回到内核2.6)。在所有三种情况下,工作流程都是相同的。如果您使用Docker,Vag犯人可以启动一台可以在所有这三个系统上运行Docker的机器(VM或远程)。

  • Vagrent知道如何配置一些高级或非平凡的东西,如网络和同步文件夹。例如:Vagrent知道如何将静态IP附加到机器或转发端口,无论您使用什么系统(VirtualBox、威睿等),配置都是相同的对于同步文件夹,Vagrent提供了多种机制来将您的本地文件传输到远程机器(VirtualBox共享文件夹、NFS、rsync、Samba[插件]等)。如果您使用的是Docker,即使是带有没有Vag犯人的VM的Docker,您也必须手动执行此操作,否则他们将不得不在这种情况下重新发明Vagrent。

  • Vagrent 1.6对基于docker的开发环境具有一流的支持。这不会在Linux上启动虚拟机,而是会在Mac和Windows上自动启动虚拟机。最终结果是使用Docker在所有平台上都是统一的,而Vag犯人仍然处理网络、同步文件夹等繁琐的细节。

为了解决我听到的支持使用Docker而不是Vagrent的具体反对意见:

  • “移动部件更少”——是的,如果你在每个项目中都专门使用Docker,这是可以的。即便如此,它也在牺牲Docker锁定的灵活性。如果你决定不在任何项目中使用Docker,无论是过去、现在还是未来,那么你会有更多的移动部件。如果你使用了Vagrent,你就有了支持其余部分的移动部件。

  • “它更快!”——一旦你有了可以运行Linux容器的主机,Docker运行容器的速度肯定比任何虚拟机启动的速度都要快。但是启动虚拟机(或远程机器)是一次性的成本。一天中,大多数Vagrent用户从未真正销毁过他们的虚拟机。这是对开发环境的奇怪优化。在Docker真正闪耀的生产环境中,我理解快速启动/关闭容器的必要性。

我希望现在可以清楚地看到,将Docker与Vagrent进行比较是非常困难的,我认为这是不正确的。对于开发环境,Vagrent更抽象,更通用。Docker(以及让它表现得像Vagrent的各种方式)是Vag犯人的一个特定用例,忽略了Vag犯人提供的所有其他功能。

总结:在高度特定的用例中,Docker当然是Vagrent的可能替代品。在大多数用例中,它不是。Vag犯人并不妨碍你使用Docker;它实际上尽其所能让你的体验更流畅。如果你发现这不是真的,我很乐意接受改进建议,因为Vag犯人的目标是与任何系统同等出色地工作。

希望这能把事情弄清楚!

我是Docker的作者。

简短的回答是,如果你想管理机器,你应该使用Vagrent。如果你想构建和运行应用程序环境,你应该使用Docker。

Docker是一个用于构建和部署应用程序的工具,它将应用程序打包到轻量级容器中。容器可以容纳几乎任何软件组件及其依赖项(可执行文件,库,配置文件等),并在有保障且可重复的运行时环境中执行。这使得构建一次应用程序并将其部署在任何地方变得非常容易——在笔记本电脑上进行测试,然后在不同的服务器上进行实时部署等。

一个常见的误解是,你只能在Linux上使用Docker。这是不正确的;你也可以在Mac和Windows上安装Docker。在Mac上安装时,Docker捆绑了一个小型LinuxVM(磁盘上有25 MB!),它充当容器的包装器。安装后,这是完全透明的;你可以以完全相同的方式使用Docker命令行。这为您提供了两全其美的优势:您可以使用容器来测试和开发您的应用程序,容器非常轻量级,易于测试并且易于移动(例如,请参阅与Docker社区共享可重用容器的示例https://hub.docker.com),并且您无需担心管理虚拟机的细节,这只是实现目的的一种手段。

从理论上讲,可以使用Vag犯人作为Docker的抽象层。

  • 首先,对于Docker来说,Vagrent不是一个好的抽象。Vagrent旨在管理虚拟机。Docker旨在管理应用程序运行时。这意味着Docker在设计上可以以更丰富的方式与应用程序交互,并拥有更多关于应用程序运行时的信息。Docker中的原语是进程、日志流、环境变量和组件之间的网络链接。Vagrent中的原语是机器、块设备和ssh密钥。Vag犯人只是在堆栈中处于较低的位置,它与容器交互的唯一方法是假装它只是另一种机器,你可以“引导”和“登录”。所以,当然,你可以使用Docker插件输入“流浪汉”,然后会发生一些漂亮的事情。它是Docker所能做的全部的替代品吗?尝试几天原生Docker,亲自看看:)

  • 第二,锁定论。“如果你把Vagrent作为一个抽象,你就不会被锁定在Docker中!”。从旨在管理机器的Vagrent的角度来看,这是非常有道理的:容器不就是另一种机器吗?就像亚马逊EC2和威睿一样,我们必须小心不要把我们的配置工具与任何特定的供应商捆绑在一起!这会造成锁定——最好用Vag犯人把它们都抽象出来。但这完全没有抓住Docker的重点。Docker不配置机器;它把你的应用程序包装在一个轻量级的便携式运行时中,可以放在任何地方。

您为应用程序选择的运行时与您如何预配机器无关!例如,将应用程序部署到其他人预配的机器(例如,您的系统管理员部署的EC2实例,可能使用Vagrent)或Vagrent根本无法预配的裸机上是非常常见的。相反,您可以使用Vagrent预配与开发您的应用程序无关的机器——例如即用型Windows IIS框或其他东西。或者您可以使用Vagrent为不使用Docker的项目预配机器——例如,它们可能结合使用rubygems和rvm进行依赖项管理和沙盒。

总结:Vagrent用于管理机器,Docker用于构建和运行应用程序环境。

同时使用两者是应用程序交付测试的重要组成部分。我才刚刚开始接触Docker,并非常努力地思考一个在构建和交付软件方面非常复杂的应用程序团队。想想经典的凤凰项目/持续交付情况。

这个想法是这样的:

  • 获取Java /Go应用程序组件并将其构建为容器(注意,不确定应用程序是应该在容器中构建还是在容器中构建安装到容器)
  • 将容器交付给Vagrent VM。
  • 对所有应用程序组件重复此操作。
  • 在要编码的组件上迭代。
  • 不断测试交付机制到Vagrent管理的VM
  • 睡个好觉,知道什么时候是时候部署容器了,集成测试比Docker之前更连续地进行。

这似乎是Mitchell关于Vag犯人只做开发的说法,结合Farley/Humble在持续交付中的思考,在逻辑上的延伸。作为开发人员,如果我能把集成测试和应用交付上的反馈回路缩得更窄,更高质量、更好的工作环境就会接踵而至。

作为一名开发人员,我不断地、始终如一地将容器交付给虚拟机,并更全面地测试应用程序,这意味着生产版本将进一步简化。

因此,我认为Vagrent正在发展成为一种利用Docker将为应用程序部署带来的一些可怕后果的方式。

它们是非常互补的。

几个月来,我一直在我的所有项目中使用VirtualBox、Vagrent和Docker的组合,并强烈感受到以下好处。

在Vagrent中,您可以完全取消任何Chef单独配置,您需要的只是准备一台运行安装docker的小型外壳脚本的机器。这意味着我的每个项目的Vagrantfile几乎相同且非常简单。

这是一个典型的Vagrantfile

# -*- mode: ruby -*-# vi: set ft=ruby :VAGRANTFILE_API_VERSION = "2"Vagrant.configure(VAGRANTFILE_API_VERSION) do |config|config.vm.box = "mark2"config.vm.box_url = "http://cloud-images.ubuntu.com/vagrant/trusty/current/trusty-server-cloudimg-amd64-vagrant-disk1.box"[3000, 5000, 2345, 15672, 5672, 15674, 27017, 28017, 9200, 9300, 11211, 55674, 61614, 55672, 5671, 61613].each do |p|config.vm.network :forwarded_port, guest: p, host: pendconfig.vm.network :private_network, ip: "192.168.56.20"config.vm.synced_folder ".", "/vagrant", :type => "nfs"config.vm.provider :virtualbox do |vb|vb.customize ["modifyvm", :id, "--memory", "2048"]vb.customize ["modifyvm", :id, "--cpus", "2"]end# Bootstrap to Dockerconfig.vm.provision :shell, path: "script/vagrant/bootstrap", :privileged => true# Build docker containersconfig.vm.provision :shell, path: "script/vagrant/docker_build", :privileged => true# Start containers# config.vm.provision :shell, path: "script/vagrant/docker_start", :privileged => trueend

安装docker的Bootstrap文件如下所示

#!/usr/bin/env bashecho 'vagrant  ALL= (ALL:ALL) NOPASSWD: ALL' >> /etc/sudoersapt-get update -yapt-get install htop -yapt-get install linux-image-extra-`uname -r` -yapt-key adv --keyserver hkp://keyserver.ubuntu.com:80 --recv-keys 36A1D7869245C8950F966E92D8576A8BA88D21E9echo deb http://get.docker.io/ubuntu docker main > /etc/apt/sources.list.d/docker.listapt-get update -yapt-get install lxc-docker -yapt-get install curl -y

现在,为了得到我需要的所有服务,我有一个docker_start脚本,看起来像这样

#!/bin/bashcd /vagrantecho Starting required service containersexport HOST_NAME=192.168.56.20# Start MongoDBdocker run --name=mongodb --detach=true --publish=27017:27017 --publish=28017:28017 dockerfile/mongodbread -t5 -n1 -r -p "Waiting for mongodb to start..." key# Start rabbitmqdocker run --name=rabbitmq --detach=true --publish=5671:5671 --publish=5672:5672 --publish=55672:55672 --publish=15672:15672 --publish=15674:15674 --publish=61613:61613 --env RABBITMQ_USER=guest --env RABBITMQ_PASS=guest rabbitmqread -t5 -n1 -r -p "Waiting for rabbitmq to start..." key# Start cachedocker run --name=memcached --detach=true --publish=11211:11211  ehazlett/memcachedread -t5 -n1 -r -p "Waiting for cache to start..." key# Start elasticsearchdocker run --name=elasticsearch --detach=true --publish=9200:9200 --publish=9300:9300 dockerfile/elasticsearchread -t5 -n1 -r -p "Waiting for elasticsearch to start..." keyecho "All services started"

在这个例子中,我正在运行MongoDB、Elastisearch、RabbitMQ和Memcacher

非docker Chef独奏配置会复杂得多。

当您进入生产环境时,将开发环境转换为主机的基础设施将获得最后一个巨大的好处,这些主机都是相同的,因为它们只有足够的配置来运行docker,这确实意味着很少的工作。

如果您有兴趣,我在自己的网站上有一篇关于开发环境的更详细的文章

实现Vag犯人/Docker开发环境

现在有了Vagrent,您可以将Docker作为提供者。http://docs.vagrantup.com/v2/docker/。可以使用Docker提供者代替VirtualBox或威睿。

请注意,您还可以使用Docker与Vag犯人一起配置。这与使用Docker作为提供者非常不同。http://docs.vagrantup.com/v2/provisioning/docker.html

这意味着您可以用Docker替换厨师木偶。您可以使用Docker作为提供者(VM)与Chef作为预配者等组合。或者您可以使用VirtualBox作为提供者,Docker作为预配者。

在实际的OracleJava杂志上有一篇关于将Docker与Vagrent(和Puppet)结合使用的非常有用的文章:

结论

Docker的轻量级容器比经典虚拟机更快并且在开发人员中变得流行,并作为CD和运营模式的一部分如果你的目的是隔离,Docker是一个很好的选择。Vagrent是一个VM管理器,使您能够编写单个VM以及进行预配。但是,它仍然是一个依赖于VirtualBox(或其他VM管理器)的VM具有相对大开销。它要求您有一个硬盘驱动器空闲,可以巨大,它需要大量的RAM,并且性能可能不是最佳的。Docker通过LXC使用内核cgroup和命名空间隔离。这意味着您使用与主机相同的内核和相同的ile系统。就抽象而言,Vagrent比Docker高一级,所以它们是配置管理工具,如Puppet广泛用于配置目标环境。重用现有使用Docker,基于木偶的解决方案很容易。您还可以切片您的解决方案,因此基础设施预配了Puppet预配中间件、业务应用程序本身或两者使用Docker;Docker由Vag犯人包装。有了这个范围的

如何在运营模式下构建、使用和编排Docker容器http://www.javamagazine.mozaicreader.com/JulyAug2015#&; pageSet=34&page=0

绝对是Docker的胜利!

您可能知道Vagrent用于虚拟机管理,而Docker用于软件容器管理。如果你不知道区别,这里是:软件容器可以与其他软件容器共享相同的机器和内核。使用容器可以节省资金,因为您不会在多个操作系统(内核)上浪费资源,您可以在每台服务器上打包更多软件,保持良好的隔离程度。

当然,这是一门新的学科,需要照顾自己的缺陷和挑战。

如果您的需求超过单机资源限制,请使用Docker Swing。