diff --git a/lib/vagrant/config/container.rb b/lib/vagrant/config/container.rb index 19f9b055e..6c109c421 100644 --- a/lib/vagrant/config/container.rb +++ b/lib/vagrant/config/container.rb @@ -7,7 +7,31 @@ module Vagrant # the completely loaded configuration values. This class is meant to # be immutable. class Container + # Initializes the configuration container. + # + # A `Vagrant::Config::top` should be passed in to initialize this. + # The container will use this top in order to separate and provide + # access to the configuration. + def initialize(top) + @top = top + end + # This returns the global configuration values. These are values + # that apply to the system as a whole, and not to a specific virtual + # machine or so on. Examples of this sort of configuration: the + # class of the host system, name of the Vagrant dotfile, etc. + def global + # For now, we just return all the configuration, until we + # separate out global vs. non-global configuration keys. + @top + end + + # This returns the configuration for a specific virtual machine. + # The values for this configuration are usually pertinent to a + # single virtual machine and do not affect the system globally. + def for_vm(name) + @top + end end end end diff --git a/lib/vagrant/config/loader.rb b/lib/vagrant/config/loader.rb index 0e3c37112..4dd4e32a1 100644 --- a/lib/vagrant/config/loader.rb +++ b/lib/vagrant/config/loader.rb @@ -19,6 +19,7 @@ module Vagrant def initialize @logger = Log4r::Logger.new("vagrant::config::loader") @sources = {} + @proc_cache = {} end # Set the configuration data for the given name. @@ -56,7 +57,16 @@ module Vagrant @load_order.each do |key| @sources[key].each do |source| @logger.debug("Loading from: #{key}") - procs_for_source(source).each do |proc| + + # Load the procs, caching them by the source key. This makes + # sure that files are only loaded once, for example. The reason + # for this is because people may put side-effect code in their + # Vagrantfiles. This assures that the side effect only occurs + # once (which is what they expect) + @proc_cache[key] ||= procs_for_source(source) + + # Call each proc with the top-level configuration. + @proc_cache[key].each do |proc| proc.call(top) end end diff --git a/test/unit/vagrant/config/loader_test.rb b/test/unit/vagrant/config/loader_test.rb index 3ef9c7b80..baf833b72 100644 --- a/test/unit/vagrant/config/loader_test.rb +++ b/test/unit/vagrant/config/loader_test.rb @@ -17,6 +17,16 @@ describe Vagrant::Config::Loader do config.vagrant.dotfile_name.should == "foo" end + it "should only load configuration files once" do + $_config_data = 0 + + instance.load_order = [:file] + instance.set(:file, temporary_file("$_config_data += 1")) + 5.times { instance.load } + + $_config_data.should == 1 + end + it "should raise proper error if there is a syntax error in a Vagrantfile" do instance.load_order = [:file] instance.set(:file, temporary_file("Vagrant:^Config"))