RLanffy 2019-07-01
Box 是一个 bundle 或者 package,它将一台虚拟机所需要的一切设施捆绑到一个单一的、可交换的文件之中,从而提供了分享的便利。
从这一点上说,Box 和 OVF 是一样的东西。不过 OVF 是具有公信力的标准格式,而 Box 则是 Vagrant 的私有格式。所以人们不免疑问既然如此、岂非我还是去 VMWare/VirtualBox 中导出 ovf 格式的比较好吧?事实上又并非这么简单,就好像 Microsoft Office 也是私有格式一样,它还是通行于全球。所以,一般地看,为着分享一个极为有效的基础设施的目的,你可能还是需要通过 Vagrant Box 特性建立你的基础设施的 VirtualBox/VMWare/KVM/Hyper-V 分发包,才能真的让世界上的其它人或许感谢你的友好;而如果你只是临时给LAN中某个人传递一个snapshot的话,就ovf好了;如果你的 team 统一使用 vagrant 为开发容器环境的话,那当然还是 box 了;如果你的 team 主力使用 docker,那就已经不在这个问题讨论范围内了。
一般的用法是:
vagrant package --base dos7bc31 --output dos7bc31.box
在这里,你首先在VirtualBox中制作了一个名为 dos7bc31 的虚拟机,并且在虚拟机中搭建了 DOS 7.1的环境和安装了 Borland C++ 3.1,然后发布此命令就能得到一个 box 文件了:
$ vagrant package --base dos71bc31 --output dos71bc31.box ==> dos7bc31: Exporting VM... ==> dos7bc31: Compressing package to: /Users/hz/vmt/dos7/dos71bc31.box $ ll total 113784 -rw-r--r-- 1 hz staff 3.0K Feb 21 10:05 Vagrantfile -rw-r--r--@ 1 hz staff 55M Feb 21 10:08 dos71bc31.box
当然,你需要为那个虚拟机准备一份 Vagrantfile,这可以用 vagrant init
在当前的空文件夹中建议一份。
LAN中,直接传输 box 给他人即可。
你也可以考虑发布 box 到公共目录中。
对于一个本地的 box 文件,可以这样添加它:
vagrant box add --name hedzr/dos71bc31 ./dos71bc31.box
然后就可以初始化相应的实例了:
mkdir test && cd test1 vagrant init hedzr/doc71bc31 vagrant up
当发布了你的box的新版本之后,接收人需要更新它。对于本地的 box 文件,更新的方法是:
vagrant box add -f --name hedzr/dos72bc31 './dos71bc31 (1).box'
如果发布者在构建 box 时正确地进行了 config.vm.box_version
的管理的话,则 -f
标志不必使用。
相关的 vagrant 命令参考如下:
package
命令用于从虚拟机提供商(例如 virtualbox)环境中已经创建了虚拟机实例中打包一个 .box 可交换文件出来。
Usage: vagrant package [options] [name|id] Options: --base NAME Name of a VM in VirtualBox to package as a base box (VirtualBox Only) --output NAME Name of the file to output --include FILE,FILE.. Comma separated additional files to package with the box --vagrantfile FILE Vagrantfile to package with the box -h, --help Print this help
box 包含一组子命令:add,list,outdated,prune,remove,repackage,update。
命令 | 描述 |
---|---|
add | 添加 box(从文件、url、短名字)到 vagrant boxes管理区,必要时自动下载它 |
list | 列出 vagrant boxes 管理区中已有的本地 boxes |
outdated | 检查本地 boxes 的时效性,有否新版本存在 |
prune | 删除本地 boxes 的旧版本,仅保留最新的一个版本 |
remove | 删除一个本地 box |
repackage | 重新打包一个本地 box,这多用于本地创建新box的过程中 |
update | 更新一个本地 box,从远程来源 |
你可以通过 vagrant box add --help
来获取相应的命令行参数参考。或者检查官网:Box。
为免填充字数只说,这里不再罗列了。
cd dos71bc31 vagrant package --base dos71bc31 --output dos71bc31.box --vagrantfile vagrant box add -f --name hedzr/dos71bc31 dos71bc31.box mkdir test1 && cd test1 vagrant init hedzr/dos71bc31 vagrant up # shutdown VM from virtualbox ... vagrant destroy -f cd - vagrant box remove hedzr/dos71bc31 -f
按照官方的说法,Vagrantfile能够被合并。
这就是说,当你通过 vagrant init
建立了一个新的虚拟机环境时,vagrant将会一次检查一系列的可用的 Vagrantfile 并将它们合并到最终为你生成的 Vagrantfile
中。而当 vagrant up
当前虚拟机时,vagrant同样会检查这一系列可用的 Vagrantfile,并依据有否变更或虚拟机有否不符等实际情况对真实的虚拟机进行配置修订。
这些可用的 Vagrantfile 包括:
vagrant init
时,此文件尚未存在故略过,当 vagrant up
时它会被检视,并根据实际情况去修订虚拟机有多种方法启用或禁用 虚拟机的 GUI 界面。
直接通过命令行:
vagrant up --gui vagrant up --headless
修改 Vagrantfile
配置文件:
config.vm.provider "virtualbox" do |v| v.gui = true end
对于大多数基于 Linux Server 的虚拟机来说,乃至于 vagrant 默认情况下,一个虚拟机总是被启动于 headless 无界面模式的。
不过即使这样,你还是可以在 VirtualBox应用程序界面中双击虚拟机缩略图或者通过虚拟机子菜单显示其 gui 界面。
有人曾钻研过这个问题,列出了一个更奇技的方法来方便你指定GUI模式与否。其方法是修改Vagrantfile加入如下片段:
# Returns true if `GUI` environment variable is set to a non-empty value. # Defaults to false def gui_enabled? !ENV.fetch('GUI', '').empty? end Vagrant.configure('2') do |config| config.vm.provider 'virtualbox' do |v| v.gui = gui_enabled? end end
然后你就可以这样来执行命令:
# for *nix system GUI=1 vagrant up # gui mode vagrant up # -headless mode # for windows SET GUI=1 vagrant up
See also: https://stackoverflow.com/a/2...
不过我觉得多余。至于我列举的原因呢,只是展示一种使用环境变量的方法,它可以被用于自行装配和分发 box。