Dustin Ingram

WritingSpeakingGithubTwitter

The Problem #

Vagrant is more or less magic. That’s why I was disappointed to find that if your Vagrantfile depends on any plugins, your magic goes from:

vagrant up

to:

vagrant plugin install some-plugin
vagrant plugin install another-plugin
vagrant plugin install still-more-plugins
vagrant up

There’s a lot of hacky solutions to this all over the internet, as well as a lot of closed issue requests and defunct “Bundler”-esque projects attempting to fix this, but none are a clean, elegant solution which won’t pollute your Vagrantfile.

The Solution #

There’s an intentionally undocumented feature of Vagrant introduced in v1.7 which gives us a solution: Vagrant will execute the contents of a .vagrantplugins file before attempting to execute the Vagrantfile. Put the following snippet in this file (updating the plugin list accordingly) and then a vagrant up will be all you need:

required_plugins = %w(
  some-plugin
  another-plugin
  still-more-plugins
)

needs_restart = false
required_plugins.each do |plugin|
  unless Vagrant.has_plugin? plugin
    system "vagrant plugin install #{plugin}"
    needs_restart = true
  end
end

if needs_restart
  exec "vagrant #{ARGV.join' '}"
end

The beauty of this snippet is that it only restarts the vagrant process once, and only if plugins needed to be installed.

PS, One More Thing #

You can list your currently installed plugins with:

vagrant plugin list

Thanks #

Thanks to mkuzmin for this tip.