diff --git a/test/acceptance/base.rb b/test/acceptance/base.rb index 16645256f..38a427359 100644 --- a/test/acceptance/base.rb +++ b/test/acceptance/base.rb @@ -2,9 +2,10 @@ require "rubygems" require "contest" require "log4r" -require File.expand_path("../helpers/config.rb", __FILE__) +require File.expand_path("../helpers/config", __FILE__) require File.expand_path("../helpers/isolated_environment", __FILE__) -require File.expand_path("../helpers/output.rb", __FILE__) +require File.expand_path("../helpers/output", __FILE__) +require File.expand_path("../helpers/virtualbox", __FILE__) # Enable logging if requested if ENV["ACCEPTANCE_LOGGING"] @@ -57,6 +58,9 @@ class AcceptanceTest < Test::Unit::TestCase end setup do + # Wait for VBoxSVC to disappear + Acceptance::VirtualBox.wait_for_vboxsvc + # Setup the environment so that we have an isolated area # to run Vagrant. We do some configuration here as well in order # to replace "vagrant" with the proper path to Vagrant as well @@ -71,6 +75,6 @@ class AcceptanceTest < Test::Unit::TestCase end teardown do - @environment.close + @environment.close if @environment end end diff --git a/test/acceptance/helpers/isolated_environment.rb b/test/acceptance/helpers/isolated_environment.rb index 46882e848..b45781596 100644 --- a/test/acceptance/helpers/isolated_environment.rb +++ b/test/acceptance/helpers/isolated_environment.rb @@ -5,6 +5,7 @@ require "log4r" require "posix-spawn" require File.expand_path("../tempdir", __FILE__) +require File.expand_path("../virtualbox", __FILE__) module Acceptance # This class manages an isolated environment for Vagrant to @@ -109,6 +110,17 @@ module Acceptance # Closes the environment, cleans up the temporary directories, etc. def close + # Only delete virtual machines if VBoxSVC is running, meaning + # that something related to VirtualBox started running in this + # environment. + delete_virtual_machines if VirtualBox.find_vboxsvc + + # Delete the temporary directory + @logger.info("Removing isolated environment: #{@tempdir.path}") + FileUtils.rm_rf(@tempdir.path) + end + + def delete_virtual_machines # Delete all virtual machines @logger.debug("Finding all virtual machines") execute("VBoxManage", "list", "vms").stdout.lines.each do |line| @@ -125,10 +137,6 @@ module Acceptance end @logger.info("Removed all virtual machines") - - # Delete the temporary directory - @logger.info("Removing isolated environment: #{@tempdir.path}") - FileUtils.rm_rf(@tempdir.path) end # This replaces a command with a replacement defined when this diff --git a/test/acceptance/helpers/virtualbox.rb b/test/acceptance/helpers/virtualbox.rb new file mode 100644 index 000000000..f63b7b69c --- /dev/null +++ b/test/acceptance/helpers/virtualbox.rb @@ -0,0 +1,36 @@ +require 'sys/proctable' + +module Acceptance + module VirtualBox + extend self + + # This method will wait for the "VBoxSVC" process to end. This will + # block during that time period. The reason for this is because only + # one "VBoxSVC" can run per user and manages all state within VirtualBox. + # Before you can run VirtualBox with a custom home directory, you must + # wait for this VBoxSVC process to die. + def wait_for_vboxsvc + time_passed = 0 + while find_vboxsvc + if time_passed > 5 + raise Exception, "VBoxSVC process is not going away." + end + + sleep 1 + time_passed += 1 + end + end + + # This method finds the VBoxSVC process and returns information about it. + # This will return "nil" if VBoxSVC is not found. + def find_vboxsvc + Sys::ProcTable.ps do |process| + if process.comm == "VBoxSVC" + return process + end + end + + nil + end + end +end diff --git a/vagrant.gemspec b/vagrant.gemspec index 5b278bde3..34762a619 100644 --- a/vagrant.gemspec +++ b/vagrant.gemspec @@ -29,6 +29,7 @@ Gem::Specification.new do |s| s.add_development_dependency "minitest", "~> 2.5.1" s.add_development_dependency "mocha" s.add_development_dependency "posix-spawn", "~> 0.3.6" + s.add_development_dependency "sys-proctable", "~> 0.9.1" s.files = `git ls-files`.split("\n") s.executables = `git ls-files`.split("\n").map{|f| f =~ /^bin\/(.*)/ ? $1 : nil}.compact