[Pkg-puppet-devel] [SCM] Puppet packaging for Debian branch, experimental, updated. debian/2.6.8-1-844-g7ec39d5

Matt Robinson matt at puppetlabs.com
Tue May 10 08:06:14 UTC 2011


The following commit has been merged in the experimental branch:
commit 2ae88067492f7922a3c4d53b6fa8c849b193f76a
Merge: 489942706726629fe0d477ebb2692c2b0b05c43e 17f673dd6fee08309970f8ff721855cf1644b45f
Author: Matt Robinson <matt at puppetlabs.com>
Date:   Fri Mar 18 14:10:24 2011 -0700

        Merge branch '2.6.x' into next
    
        * 2.6.x: (36 commits)
          Updated CHANGELOG for 2.6.7rc1
          (#5073) Download plugins even if you're filtering on tags
          Fix #5610: Prevent unnecessary RAL lookups
          Revert "Merge branch 'ticket/2.6.x/5605' of git://github.com/stschulte/puppet into 2.6.next"
          (#6723) Fix withenv environment restoration bug
          (#6689) Remove extraneous include of Puppet::Util in InventoryActiveRecord
          Remove extra trailing whitespace from lib/puppet/resource.rb
          (#5428) More fully "stub" Puppet::Resource::Reference for use with storedconfigs
          (#6707) Fix typo in rest_authconfig.rb
          (#6689) Make inventory_active_record terminus search quickly
          (#5392) Give a better error when realizing a non-existant resource
          (#2645) Adding a less-stubby test to verify the "system" attribute's behavior
          Update CHANGELOG for 2.6.6
          maint: Remove serialization of InventoryFact values
          maint: Rename InventoryHost to InventoryNode
          Fixed #2645 - Added support for creating system users
          maint: Remove spec run noise
          maint:Refactor of mount provider integration tests
          (#6338) Support searching on metadata in InventoryActiveRecord terminus
          (#6338) Implement search for InventoryActiveRecord facts terminus
          ...
    
        This merge includes essentially reverting #4904's change to the mount
        type since tests that came in from 2.6.x specified different
        behavior and what's correct is not clear to me.  I've reopened #4904 and
        added it to our backlog, and talked to Nigel about the RFC that's
        currently out on the puppet-users mailing list for a bigger refactor of
        how the mount provider works.
    
        Manually Resolved Conflicts:
            spec/spec_helper.rb
            spec/unit/indirector/queue_spec.rb

diff --combined install.rb
index 72acb24,e8755e0..6854363
--- a/install.rb
+++ b/install.rb
@@@ -53,6 -53,18 +53,6 @@@ rescue LoadErro
    $haverdoc = false
  end
  
 -begin
 -  if $haverdoc
 -    ronn = %x{which ronn}
 -    $haveman = true
 -  else
 -    $haveman = false
 -  end
 -rescue
 -  puts "Missing ronn; skipping man page creation"
 -  $haveman = false
 -end
 -
  PREREQS = %w{openssl facter xmlrpc/client xmlrpc/server cgi}
  MIN_FACTER_VERSION = 1.5
  
@@@ -166,6 -178,15 +166,6 @@@ def prepare_installatio
    end
  
  
 -  if $haveman
 -    InstallOptions.man = true
 -    if $operatingsystem == "windows"
 -      InstallOptions.man  = false
 -    end
 -  else
 -    InstallOptions.man = false
 -  end
 -
    InstallOptions.tests = true
  
    ARGV.options do |opts|
@@@ -177,6 -198,9 +177,6 @@@
      opts.on('--[no-]ri', 'Prevents the creation of RI output.', 'Default off on mswin32.') do |onri|
        InstallOptions.ri = onri
      end
 -    opts.on('--[no-]man', 'Prevents the creation of man pages.', 'Default on.') do |onman|
 -    InstallOptions.man = onman
 -    end
      opts.on('--[no-]tests', 'Prevents the execution of unit tests.', 'Default on.') do |ontest|
        InstallOptions.tests = ontest
      end
@@@ -209,6 -233,7 +209,6 @@@
      end
      opts.on('--full', 'Performs a full installation. All', 'optional installation steps are run.') do |full|
        InstallOptions.rdoc    = true
 -      InstallOptions.man     = true
        InstallOptions.ri      = true
        InstallOptions.tests   = true
        InstallOptions.configs = true
@@@ -275,33 -300,28 +275,28 @@@
      mandir = Config::CONFIG['mandir']
    end
  
+   # This is the new way forward
+   if not InstallOptions.destdir.nil?
+     destdir = InstallOptions.destdir
    # To be deprecated once people move over to using --destdir option
-   if (destdir = ENV['DESTDIR'])
-     configdir = "#{destdir}#{configdir}"
-     bindir = "#{destdir}#{bindir}"
-     sbindir = "#{destdir}#{sbindir}"
-     mandir = "#{destdir}#{mandir}"
-     sitelibdir = "#{destdir}#{sitelibdir}"
+   elsif ENV['DESTDIR'] != nil?
+     destdir = ENV['DESTDIR']
+     warn "DESTDIR is deprecated. Use --destdir instead."
+   else
+     destdir = ''
+   end
  
-     FileUtils.makedirs(configdir) if InstallOptions.configs
-     FileUtils.makedirs(bindir)
-     FileUtils.makedirs(sbindir)
-     FileUtils.makedirs(mandir)
-     FileUtils.makedirs(sitelibdir)
-   # This is the new way forward
-   elsif (destdir = InstallOptions.destdir)
-     configdir = "#{destdir}#{configdir}"
-     bindir = "#{destdir}#{bindir}"
-     sbindir = "#{destdir}#{sbindir}"
-     mandir = "#{destdir}#{mandir}"
-     sitelibdir = "#{destdir}#{sitelibdir}"
+   configdir = "#{destdir}#{configdir}"
+   bindir = "#{destdir}#{bindir}"
+   sbindir = "#{destdir}#{sbindir}"
+   mandir = "#{destdir}#{mandir}"
+   sitelibdir = "#{destdir}#{sitelibdir}"
  
-     FileUtils.makedirs(configdir) if InstallOptions.configs
-     FileUtils.makedirs(bindir)
-     FileUtils.makedirs(sbindir)
-     FileUtils.makedirs(mandir)
-     FileUtils.makedirs(sitelibdir)
-   end
+   FileUtils.makedirs(configdir) if InstallOptions.configs
+   FileUtils.makedirs(bindir)
+   FileUtils.makedirs(sbindir)
+   FileUtils.makedirs(mandir)
+   FileUtils.makedirs(sitelibdir)
  
    tmpdirs << bindir
  
@@@ -343,6 -363,33 +338,6 @@@ def build_ri(files
    end
  end
  
 -def build_man(bins, sbins)
 -  return unless $haveman
 -  begin
 -    # Locate ronn
 -    ronn = %x{which ronn}
 -    ronn.chomp!
 -    # Create puppet.conf.5 man page
 -    %x{bin/puppetdoc --reference configuration > ./man/man5/puppetconf.5.ronn}
 -    %x{#{ronn} -r ./man/man5/puppetconf.5.ronn}
 -    File.move("./man/man5/puppetconf.5", "./man/man5/puppet.conf.5")
 -    File.unlink("./man/man5/puppetconf.5.ronn")
 -
 -    # Create binary man pages
 -    binary = bins + sbins
 -    binary.each do |bin|
 -      b = bin.gsub( /(bin|sbin)\//, "")
 -      %x{#{bin} --help > ./man/man8/#{b}.8.ronn}
 -      %x{#{ronn} -r ./man/man8/#{b}.8.ronn}
 -      File.unlink("./man/man8/#{b}.8.ronn")
 -    end
 -
 -rescue SystemCallError
 -  $stderr.puts "Couldn't build man pages: " + $ERROR_INFO
 -  $stderr.puts "Continuing with install..."
 -  end
 -end
 -
  def run_tests(test_list)
      require 'test/unit/ui/console/testrunner'
      $LOAD_PATH.unshift "lib"
@@@ -436,6 -483,7 +431,6 @@@ prepare_installatio
  #run_tests(tests) if InstallOptions.tests
  #build_rdoc(rdoc) if InstallOptions.rdoc
  #build_ri(ri) if InstallOptions.ri
 -#build_man(bins, sbins) if InstallOptions.man
  do_configs(configs, InstallOptions.config_dir) if InstallOptions.configs
  do_bins(sbins, InstallOptions.sbin_dir)
  do_bins(bins, InstallOptions.bin_dir)
diff --combined lib/puppet/network/rest_authconfig.rb
index 9e36324,e606761..cf76978
--- a/lib/puppet/network/rest_authconfig.rb
+++ b/lib/puppet/network/rest_authconfig.rb
@@@ -31,14 -31,14 +31,14 @@@ module Puppe
      # check wether this request is allowed in our ACL
      # raise an Puppet::Network::AuthorizedError if the request
      # is denied.
 -    def allowed?(request)
 +    def allowed?(indirection, method, key, params)
        read
  
        # we're splitting the request in part because
        # fail_on_deny could as well be called in the XMLRPC context
        # with a ClientRequest.
  
 -      if authorization_failure_exception = @rights.is_request_forbidden_and_why?(request)
 +      if authorization_failure_exception = @rights.is_request_forbidden_and_why?(indirection, method, key, params)
          Puppet.warning("Denying access: #{authorization_failure_exception}")
          raise authorization_failure_exception
        end
@@@ -61,7 -61,7 +61,7 @@@
      def insert_default_acl
        DEFAULT_ACL.each do |acl|
          unless rights[acl[:acl]]
-           Puppet.info "Inserting default '#{acl[:acl]}'(#{acl[:authenticated] ? "auth" : "non-auth"}) acl because #{( !exists? ? "#{Puppet[:rest_authconfig]} doesn't exist" : "none where found in '#{@file}'")}"
+           Puppet.info "Inserting default '#{acl[:acl]}'(#{acl[:authenticated] ? "auth" : "non-auth"}) ACL because #{( !exists? ? "#{Puppet[:rest_authconfig]} doesn't exist" : "none were found in '#{@file}'")}"
            mk_acl(acl)
          end
        end
diff --combined lib/puppet/type/exec.rb
index 033183a,5ed2b10..ae57950
--- a/lib/puppet/type/exec.rb
+++ b/lib/puppet/type/exec.rb
@@@ -22,7 -22,9 +22,9 @@@ module Puppe
        to native Puppet types as quickly as possible.  If you find that
        you are doing a lot of work with `exec`, please at least notify
        us at Puppet Labs what you are doing, and hopefully we can work with
-       you to get a native resource type for the work you are doing."
+       you to get a native resource type for the work you are doing.
+       
+       **Autorequires:** If Puppet is managing an exec's cwd or the executable file used in an exec's command, the exec resource will autorequire those files. If Puppet is managing the user that an exec should run as, the exec resource will autorequire that user."
  
      require 'open3'
  
@@@ -211,6 -213,15 +213,6 @@@
        end
      end
  
 -    newparam(:env) do
 -      desc "This parameter is deprecated. Use 'environment' instead."
 -
 -      munge do |value|
 -        warning "'env' is deprecated on exec; use 'environment' instead."
 -        resource[:environment] = value
 -      end
 -    end
 -
      newparam(:environment) do
        desc "Any additional environment variables you want to set for a
          command.  Note that if you use this to set PATH, it will override
diff --combined lib/puppet/type/file.rb
index 963b9e5,e1a4ecb..16b1f96
--- a/lib/puppet/type/file.rb
+++ b/lib/puppet/type/file.rb
@@@ -22,7 -22,9 +22,9 @@@ Puppet::Type.newtype(:file) d
      If you find that you are often copying files in from a central
      location, rather than using native resources, please contact
      Puppet Labs and we can hopefully work with you to develop a
-     native resource to support what you are doing."
+     native resource to support what you are doing.
+     
+     **Autorequires:** If Puppet is managing the user or group that owns a file, the file resource will autorequire them. If Puppet is managing any parent directories of a file, the file resource will autorequire them."
  
    def self.title_patterns
      [ [ /^(.*?)\/*\Z/m, [ [ :path, lambda{|x| x} ] ] ] ]
@@@ -577,7 -579,7 +579,7 @@@
  
    def perform_recursion(path)
  
 -    Puppet::FileServing::Metadata.search(
 +    Puppet::FileServing::Metadata.indirection.search(
  
        path,
        :links => self[:links],
diff --combined lib/puppet/type/zfs.rb
index be18ab5,6f04bdd..7123f8a
--- a/lib/puppet/type/zfs.rb
+++ b/lib/puppet/type/zfs.rb
@@@ -1,6 -1,8 +1,8 @@@
  module Puppet
    newtype(:zfs) do
-     @doc = "Manage zfs. Create destroy and set properties on zfs instances."
+     @doc = "Manage zfs. Create destroy and set properties on zfs instances.
+ 
+ **Autorequires:** If Puppet is managing the zpool at the root of this zfs instance, the zfs resource will autorequire it. If Puppet is managing any parent zfs instances, the zfs resource will autorequire them."
  
      ensurable
  
@@@ -12,26 -14,6 +14,26 @@@
        desc "The mountpoint property."
      end
  
 +    newproperty(:recordsize) do
 +      desc "The recordsize property."
 +    end
 +
 +    newproperty(:aclmode) do
 +      desc "The aclmode property."
 +    end
 +
 +    newproperty(:aclinherit) do
 +      desc "The aclinherit property."
 +    end
 +
 +    newproperty(:primarycache) do
 +      desc "The primarycache property."
 +    end
 +
 +    newproperty(:secondarycache) do
 +      desc "The secondarycache property."
 +    end
 +
      newproperty(:compression) do
        desc "The compression property."
      end
diff --combined lib/puppet/type/zone.rb
index c7c2aa1,471619c..1bae931
--- a/lib/puppet/type/zone.rb
+++ b/lib/puppet/type/zone.rb
@@@ -1,5 -1,7 +1,7 @@@
  Puppet::Type.newtype(:zone) do
-   @doc = "Solaris zones."
+   @doc = "Solaris zones.
+ 
+ **Autorequires:** If Puppet is managing the directory specified as the root of the zone's filesystem (with the `path` attribute), the zone resource will autorequire that directory."
  
    # These properties modify the zone configuration, and they need to provide
    # the text separately from syncing it, so all config statements can be rolled
@@@ -282,33 -284,6 +284,33 @@@
      end
    end
  
 +  newproperty(:dataset, :parent => ZoneMultiConfigProperty) do
 +    desc "The list of datasets delegated to the non global zone from the
 +      global zone.  All datasets must be zfs filesystem names which is
 +      different than the mountpoint." 
 +
 +    validate do |value|
 +      unless value !~ /^\//
 +        raise ArgumentError, "Datasets must be the name of a zfs filesystem"
 +      end
 +    end
 +
 +    # Add a zfs filesystem to our list of datasets.
 +    def add(dataset)
 +      "add dataset\nset name=#{dataset}\nend"
 +    end
 +
 +    # Remove a zfs filesystem from our list of datasets.
 +    def rm(dataset)
 +      "remove dataset name=#{dataset}"
 +    end
 +
 +    def should
 +      @should
 +    end
 +  end
 +
 +
    newproperty(:inherit, :parent => ZoneMultiConfigProperty) do
      desc "The list of directories that the zone inherits from the global
        zone.  All directories must be fully qualified."
@@@ -413,23 -388,6 +415,23 @@@
      end
    end
  
 +  # If Puppet is also managing the zfs filesystem which is the zone dataset
 +  # then list it as a prerequisite.  Zpool's get autorequired by the zfs
 +  # type.  We just need to autorequire the dataset zfs itself as the zfs type
 +  # will autorequire all of the zfs parents and zpool.
 +  autorequire(:zfs) do
 +
 +  # Check if we have datasets in our zone configuration
 +    if @parameters.include? :dataset
 +      reqs = []
 +      # Autorequire each dataset
 +      self[:dataset].each { |value|
 +        reqs << value
 +      }
 +      reqs
 +    end
 +  end
 +
    def validate_ip(ip, name)
        IPAddr.new(ip) if ip
    rescue ArgumentError
diff --combined spec/spec_helper.rb
index b23b3d9,ae4edb2..d7f546b
--- a/spec/spec_helper.rb
+++ b/spec/spec_helper.rb
@@@ -6,6 -6,7 +6,6 @@@ dir = File.expand_path(File.dirname(__F
  $LOAD_PATH.unshift("#{dir}/")
  $LOAD_PATH.unshift("#{dir}/lib") # a spec-specific test lib dir
  $LOAD_PATH.unshift("#{dir}/../lib")
 -$LOAD_PATH.unshift("#{dir}/../test/lib")
  
  # Don't want puppet getting the command line arguments for rake or autotest
  ARGV.clear
@@@ -19,15 -20,46 +19,15 @@@ module PuppetSpe
    FIXTURE_DIR = File.join(dir = File.expand_path(File.dirname(__FILE__)), "fixtures") unless defined?(FIXTURE_DIR)
  end
  
 -module PuppetTest
 -end
 -
  require 'lib/puppet_spec/files'
 +require 'lib/puppet_spec/fixtures'
  require 'monkey_patches/alias_should_to_must'
  require 'monkey_patches/publicize_methods'
  
  RSpec.configure do |config|
 -  config.mock_with :mocha
 +  include PuppetSpec::Fixtures
  
 -  config.after :each do
 -    Puppet.settings.clear
 -    Puppet::Node::Environment.clear
 -    Puppet::Util::Storage.clear
 -    Puppet::Util::ExecutionStub.reset
 -
 -    if defined?($tmpfiles)
 -      $tmpfiles.each do |file|
 -        file = File.expand_path(file)
 -        if Puppet.features.posix? and file !~ /^\/tmp/ and file !~ /^\/var\/folders/
 -          puts "Not deleting tmpfile #{file} outside of /tmp or /var/folders"
 -          next
 -        elsif Puppet.features.microsoft_windows?
 -          tempdir = File.expand_path(File.join(Dir::LOCAL_APPDATA, "Temp"))
 -          if file !~ /^#{tempdir}/
 -            puts "Not deleting tmpfile #{file} outside of #{tempdir}"
 -            next
 -          end
 -        end
 -        if FileTest.exist?(file)
 -          system("chmod -R 755 '#{file}'")
 -          system("rm -rf '#{file}'")
 -        end
 -      end
 -      $tmpfiles.clear
 -    end
 -
 -    @logs.clear
 -    Puppet::Util::Log.close_all
 -  end
 +  config.mock_with :mocha
  
    config.before :each do
      # these globals are set by Application
@@@ -44,18 -76,7 +44,19 @@@
      Puppet.settings[:bindaddress] = "127.0.0.1"
  
      @logs = []
 -    Puppet::Util::Log.newdestination(@logs)
 +    Puppet::Util::Log.newdestination(Puppet::Test::LogCollector.new(@logs))
 +  end
 +
 +  config.after :each do
 +    Puppet.settings.clear
 +    Puppet::Node::Environment.clear
 +    Puppet::Util::Storage.clear
++    Puppet::Util::ExecutionStub.reset
 +
 +    PuppetSpec::Files.cleanup
 +
 +    @logs.clear
 +    Puppet::Util::Log.close_all
    end
  end
  
diff --combined spec/unit/configurer/downloader_spec.rb
index b2485cc,4080263..266a96b
--- a/spec/unit/configurer/downloader_spec.rb
+++ b/spec/unit/configurer/downloader_spec.rb
@@@ -1,10 -1,12 +1,12 @@@
  #!/usr/bin/env ruby
  
 -require File.dirname(__FILE__) + '/../../spec_helper'
 +require File.expand_path(File.dirname(__FILE__) + '/../../spec_helper')
  
  require 'puppet/configurer/downloader'
  
  describe Puppet::Configurer::Downloader do
+   require 'puppet_spec/files'
+   include PuppetSpec::Files
    it "should require a name" do
      lambda { Puppet::Configurer::Downloader.new }.should raise_error(ArgumentError)
    end
@@@ -96,25 -98,35 +98,35 @@@
  
    describe "when creating the catalog to do the downloading" do
      before do
-       @dler = Puppet::Configurer::Downloader.new("foo", "path", "source")
+       @dler = Puppet::Configurer::Downloader.new("foo", "/download/path", "source")
      end
  
      it "should create a catalog and add the file to it" do
-       file = mock 'file'
-       catalog = mock 'catalog'
- 
-       @dler.expects(:file).returns file
- 
-       Puppet::Resource::Catalog.expects(:new).returns catalog
-       catalog.expects(:add_resource).with(file)
+       catalog = @dler.catalog
+       catalog.resources.size.should == 1
+       catalog.resources.first.class.should == Puppet::Type::File
+       catalog.resources.first.name.should == "/download/path"
+     end
  
-       @dler.catalog.should equal(catalog)
+     it "should specify that it is not managing a host catalog" do
+       @dler.catalog.host_config.should == false
      end
+ 
    end
  
    describe "when downloading" do
      before do
-       @dler = Puppet::Configurer::Downloader.new("foo", "path", "source")
+       @dl_name = tmpfile("downloadpath")
+       source_name = tmpfile("source")
+       File.open(source_name, 'w') {|f| f.write('hola mundo') }
+       @dler = Puppet::Configurer::Downloader.new("foo", @dl_name, source_name)
+     end
+ 
+     it "should not skip downloaded resources when filtering on tags" do
+       Puppet[:tags] = 'maytag'
+       @dler.evaluate
+ 
+       File.exists?(@dl_name).should be_true
      end
  
      it "should log that it is downloading" do
diff --combined spec/unit/indirector/facts/inventory_active_record_spec.rb
index 0000000,9558abd..43b9fa3
mode 000000,100644..100644
--- a/spec/unit/indirector/facts/inventory_active_record_spec.rb
+++ b/spec/unit/indirector/facts/inventory_active_record_spec.rb
@@@ -1,0 -1,163 +1,164 @@@
+ #!/usr/bin/env ruby
+ 
+ require File.dirname(__FILE__) + '/../../../spec_helper'
+ require 'sqlite3' rescue nil
+ require 'tempfile'
+ require 'puppet/rails'
+ 
+ describe "Puppet::Node::Facts::InventoryActiveRecord", :if => (Puppet.features.rails? and defined? SQLite3) do
+   let(:terminus) { Puppet::Node::Facts::InventoryActiveRecord.new }
+ 
+   before :all do
+     require 'puppet/indirector/facts/inventory_active_record'
+     @dbfile = Tempfile.new("testdb")
+     @dbfile.close
+   end
+ 
+   after :all do
+     Puppet::Node::Facts.indirection.reset_terminus_class
+     @dbfile.unlink
+   end
+ 
+   before :each do
 -    Puppet::Node::Facts.terminus_class = :inventory_active_record
++    Puppet::Node::Facts.indirection.terminus_class = :inventory_active_record
+     Puppet[:dbadapter]  = 'sqlite3'
+     Puppet[:dblocation] = @dbfile.path
+     Puppet[:railslog] = "/dev/null"
+     Puppet::Rails.init
+   end
+ 
+   after :each do
+     Puppet::Rails.teardown
+   end
+ 
+   describe "#save" do
+     it "should use an existing node if possible" do
+       node = Puppet::Rails::InventoryNode.new(:name => "foo", :timestamp => Time.now)
+       node.save
 -      Puppet::Node::Facts.new("foo", "uptime_days" => "60", "kernel" => "Darwin").save
++      facts = Puppet::Node::Facts.new("foo", "uptime_days" => "60", "kernel" => "Darwin")
++      Puppet::Node::Facts.indirection.save(facts)
+ 
+       Puppet::Rails::InventoryNode.count.should == 1
+       Puppet::Rails::InventoryNode.first.should == node
+     end
+ 
+     it "should create a new node if one can't be found" do
+       # This test isn't valid if there are nodes to begin with
+       Puppet::Rails::InventoryNode.count.should == 0
+ 
 -      Puppet::Node::Facts.new("foo", "uptime_days" => "60", "kernel" => "Darwin").save
++      facts = Puppet::Node::Facts.new("foo", "uptime_days" => "60", "kernel" => "Darwin")
++      Puppet::Node::Facts.indirection.save(facts)
+ 
+       Puppet::Rails::InventoryNode.count.should == 1
+       Puppet::Rails::InventoryNode.first.name.should == "foo"
+     end
+ 
+     it "should save the facts" do
 -      Puppet::Node::Facts.new("foo", "uptime_days" => "60", "kernel" => "Darwin").save
++      facts = Puppet::Node::Facts.new("foo", "uptime_days" => "60", "kernel" => "Darwin")
++      Puppet::Node::Facts.indirection.save(facts)
+ 
+       Puppet::Rails::InventoryFact.all.map{|f| [f.name,f.value]}.should =~ [["uptime_days","60"],["kernel","Darwin"]]
+     end
+ 
+     it "should remove the previous facts for an existing node" do
 -      Puppet::Node::Facts.new("foo", "uptime_days" => "30", "kernel" => "Darwin").save
++      facts = Puppet::Node::Facts.new("foo", "uptime_days" => "30", "kernel" => "Darwin")
++      Puppet::Node::Facts.indirection.save(facts)
+       bar_facts = Puppet::Node::Facts.new("bar", "uptime_days" => "35", "kernel" => "Linux")
+       foo_facts = Puppet::Node::Facts.new("foo", "uptime_days" => "60", "is_virtual" => "false")
 -      bar_facts.save
 -      foo_facts.save
++      Puppet::Node::Facts.indirection.save(bar_facts)
++      Puppet::Node::Facts.indirection.save(foo_facts)
+ 
 -      Puppet::Node::Facts.find("bar").should == bar_facts
 -      Puppet::Node::Facts.find("foo").should == foo_facts
++      Puppet::Node::Facts.indirection.find("bar").should == bar_facts
++      Puppet::Node::Facts.indirection.find("foo").should == foo_facts
+       Puppet::Rails::InventoryFact.all.map{|f| [f.name,f.value]}.should_not include(["uptime_days", "30"], ["kernel", "Darwin"])
+     end
+   end
+ 
+   describe "#find" do
+     before do
+       @foo_facts = Puppet::Node::Facts.new("foo", "uptime_days" => "60", "kernel" => "Darwin")
+       @bar_facts = Puppet::Node::Facts.new("bar", "uptime_days" => "30", "kernel" => "Linux")
 -      @foo_facts.save
 -      @bar_facts.save
++      Puppet::Node::Facts.indirection.save(@foo_facts)
++      Puppet::Node::Facts.indirection.save(@bar_facts)
+     end
+ 
+     it "should identify facts by node name" do
 -      Puppet::Node::Facts.find("foo").should == @foo_facts
++      Puppet::Node::Facts.indirection.find("foo").should == @foo_facts
+     end
+ 
+     it "should return nil if no node instance can be found" do
 -      Puppet::Node::Facts.find("non-existent node").should == nil
++      Puppet::Node::Facts.indirection.find("non-existent node").should == nil
+     end
+   end
+ 
+   describe "#search" do
+     def search_request(conditions)
+       Puppet::Indirector::Request.new(:facts, :search, nil, conditions)
+     end
+ 
+     before :each do
+       @now = Time.now
+       @foo = Puppet::Node::Facts.new("foo", "fact1" => "value1", "fact2" => "value2", "uptime_days" => "30")
+       @bar = Puppet::Node::Facts.new("bar", "fact1" => "value1", "uptime_days" => "60")
+       @baz = Puppet::Node::Facts.new("baz", "fact1" => "value2", "fact2" => "value1", "uptime_days" => "90")
+       @bat = Puppet::Node::Facts.new("bat")
+       @foo.timestamp = @now - 3600*1
+       @bar.timestamp = @now - 3600*3
+       @baz.timestamp = @now - 3600*5
+       @bat.timestamp = @now - 3600*7
 -      @foo.save
 -      @bar.save
 -      @baz.save
 -      @bat.save
++      [@foo, @bar, @baz, @bat].each {|facts| Puppet::Node::Facts.indirection.save(facts)}
+     end
+ 
+     it "should return node names that match 'equal' constraints" do
+       request = search_request('facts.fact1.eq' => 'value1',
+                                'facts.fact2.eq' => 'value2')
+       terminus.search(request).should == ["foo"]
+     end
+ 
+     it "should return node names that match 'not equal' constraints" do
+       request = search_request('facts.fact1.ne' => 'value2')
+       terminus.search(request).should == ["bar","foo"]
+     end
+ 
+     it "should return node names that match strict inequality constraints" do
+       request = search_request('facts.uptime_days.gt' => '20',
+                                'facts.uptime_days.lt' => '70')
+       terminus.search(request).should == ["bar","foo"]
+     end
+ 
+     it "should return node names that match non-strict inequality constraints" do
+       request = search_request('facts.uptime_days.ge' => '30',
+                                'facts.uptime_days.le' => '60')
+       terminus.search(request).should == ["bar","foo"]
+     end
+ 
+     it "should return node names whose facts are within a given timeframe" do
+       request = search_request('meta.timestamp.ge' => @now - 3600*5,
+                                'meta.timestamp.le' => @now - 3600*1)
+       terminus.search(request).should == ["bar","baz","foo"]
+     end
+ 
+     it "should return node names whose facts are from a specific time" do
+       request = search_request('meta.timestamp.eq' => @now - 3600*3)
+       terminus.search(request).should == ["bar"]
+     end
+ 
+     it "should return node names whose facts are not from a specific time" do
+       request = search_request('meta.timestamp.ne' => @now - 3600*1)
+       terminus.search(request).should == ["bar","bat","baz"]
+     end
+ 
+     it "should perform strict searches on nodes by timestamp" do
+       request = search_request('meta.timestamp.gt' => @now - 3600*5,
+                                'meta.timestamp.lt' => @now - 3600*1)
+       terminus.search(request).should == ["bar"]
+     end
+ 
+     it "should search nodes based on both facts and timestamp values" do
+       request = search_request('facts.uptime_days.gt' => '45',
+                                'meta.timestamp.lt'    => @now - 3600*4)
+       terminus.search(request).should == ["baz"]
+     end
+   end
+ end
+ 
diff --combined spec/unit/module_spec.rb
index 8f1c794,0b4873f..54f5444
--- a/spec/unit/module_spec.rb
+++ b/spec/unit/module_spec.rb
@@@ -1,6 -1,6 +1,6 @@@
  #!/usr/bin/env ruby
  
 -require File.dirname(__FILE__) + '/../spec_helper'
 +require File.expand_path(File.dirname(__FILE__) + '/../spec_helper')
  
  describe Puppet::Module do
    before do
@@@ -367,9 -367,9 +367,9 @@@
      mod.stubs(:path).returns "/a/foo"
      FileTest.expects(:exist?).with("/a/foo/plugins").returns true
  
-     mod.expects(:warning)
- 
      mod.plugin_directory.should == "/a/foo/plugins"
+     @logs.first.message.should == "using the deprecated 'plugins' directory for ruby extensions; please move to 'lib'"
+     @logs.first.level.should == :warning
    end
  
    it "should default to 'lib' for the plugins directory" do
diff --combined spec/unit/network/handler/fileserver_spec.rb
index b1306c6,9d34e9c..014b82e
--- a/spec/unit/network/handler/fileserver_spec.rb
+++ b/spec/unit/network/handler/fileserver_spec.rb
@@@ -1,6 -1,6 +1,6 @@@
  #!/usr/bin/env ruby
  
 -require File.dirname(__FILE__) + '/../../../spec_helper'
 +require File.expand_path(File.dirname(__FILE__) + '/../../../spec_helper')
  
  require 'puppet/network/handler/fileserver'
  
@@@ -158,7 -158,7 +158,7 @@@ describe Puppet::Network::Handler::File
      end
  
      it "should not fail for inexistant plugins type" do
-       lambda { @mount.list("puppet/parser",true,false) }.should_not raise_error
+       @mount.list("puppet/parser",true,false)
      end
  
    end
diff --combined spec/unit/parser/ast/collection_spec.rb
index a495bca,cc33075..99abc99
--- a/spec/unit/parser/ast/collection_spec.rb
+++ b/spec/unit/parser/ast/collection_spec.rb
@@@ -1,23 -1,24 +1,24 @@@
  #!/usr/bin/env ruby
  
 -require File.dirname(__FILE__) + '/../../../spec_helper'
 +require File.expand_path(File.dirname(__FILE__) + '/../../../spec_helper')
  
  describe Puppet::Parser::AST::Collection do
    before :each do
-     @scope = stub_everything 'scope'
-     @mytype = stub_everything('mytype')
-     @scope.stubs(:find_resource_type).returns @mytype
-     @compiler = stub_everything 'compile'
-     @scope.stubs(:compiler).returns(@compiler)
+     @mytype = Puppet::Resource::Type.new(:definition, "mytype")
+     @environment = Puppet::Node::Environment.new
+     @environment.known_resource_types.add @mytype
+ 
+     @compiler = Puppet::Parser::Compiler.new(Puppet::Node.new("foonode", :environment => @environment))
+     @scope = Puppet::Parser::Scope.new(:compiler => @compiler)
  
      @overrides = stub_everything 'overrides'
      @overrides.stubs(:is_a?).with(Puppet::Parser::AST).returns(true)
- 
    end
  
    it "should evaluate its query" do
      query = mock 'query'
      collection = Puppet::Parser::AST::Collection.new :query => query, :form => :virtual
+     collection.type = 'mytype'
  
      query.expects(:safeevaluate).with(@scope)
  
@@@ -26,8 -27,8 +27,8 @@@
  
    it "should instantiate a Collector for this type" do
      collection = Puppet::Parser::AST::Collection.new :form => :virtual, :type => "test"
-     @test_type = stub 'type', :name => 'test'
-     @scope.expects(:find_resource_type).with('test').returns @test_type
+     @test_type = Puppet::Resource::Type.new(:definition, "test")
+     @environment.known_resource_types.add @test_type
  
      Puppet::Parser::Collector.expects(:new).with(@scope, "test", nil, nil, :virtual)
  
@@@ -35,7 -36,7 +36,7 @@@
    end
  
    it "should tell the compiler about this collector" do
-     collection = Puppet::Parser::AST::Collection.new :form => :virtual, :type => "test"
+     collection = Puppet::Parser::AST::Collection.new :form => :virtual, :type => "mytype"
      Puppet::Parser::Collector.stubs(:new).returns("whatever")
  
      @compiler.expects(:add_collection).with("whatever")
@@@ -45,7 -46,7 +46,7 @@@
  
    it "should evaluate overriden paramaters" do
      collector = stub_everything 'collector'
-     collection = Puppet::Parser::AST::Collection.new :form => :virtual, :type => "test", :override => @overrides
+     collection = Puppet::Parser::AST::Collection.new :form => :virtual, :type => "mytype", :override => @overrides
      Puppet::Parser::Collector.stubs(:new).returns(collector)
  
      @overrides.expects(:safeevaluate).with(@scope)
@@@ -55,7 -56,7 +56,7 @@@
  
    it "should tell the collector about overrides" do
      collector = mock 'collector'
-     collection = Puppet::Parser::AST::Collection.new :form => :virtual, :type => "test", :override => @overrides
+     collection = Puppet::Parser::AST::Collection.new :form => :virtual, :type => "mytype", :override => @overrides
      Puppet::Parser::Collector.stubs(:new).returns(collector)
  
      collector.expects(:add_override)
@@@ -63,5 -64,8 +64,8 @@@
      collection.evaluate(@scope)
    end
  
- 
+   it "should fail when evaluating undefined resource types" do
+     collection = Puppet::Parser::AST::Collection.new :form => :virtual, :type => "bogus"
+     lambda { collection.evaluate(@scope) }.should raise_error "Resource type bogus doesn't exist"
+   end
  end
diff --combined spec/unit/parser/parser_spec.rb
index 233de23,2ed279f..01cdcb9
--- a/spec/unit/parser/parser_spec.rb
+++ b/spec/unit/parser/parser_spec.rb
@@@ -1,10 -1,10 +1,10 @@@
  #!/usr/bin/env ruby
  
 -require File.dirname(__FILE__) + '/../../spec_helper'
 +require File.expand_path(File.dirname(__FILE__) + '/../../spec_helper')
  
  describe Puppet::Parser do
  
 -  ast = Puppet::Parser::AST
 +  Puppet::Parser::AST
  
    before :each do
      @known_resource_types = Puppet::Resource::TypeCollection.new("development")
@@@ -64,16 -64,14 +64,16 @@@
        lambda { @parser.parse("$var += ") }.should raise_error
      end
  
 -    it "should call ast::VarDef with append=true" do
 -      ast::VarDef.expects(:new).with { |h| h[:append] == true }
 -      @parser.parse("$var += 2")
 +    it "should create ast::VarDef with append=true" do
 +      vardef = @parser.parse("$var += 2").code[0]
 +      vardef.should be_a(Puppet::Parser::AST::VarDef)
 +      vardef.append.should == true
      end
  
      it "should work with arrays too" do
 -      ast::VarDef.expects(:new).with { |h| h[:append] == true }
 -      @parser.parse("$var += ['test']")
 +      vardef = @parser.parse("$var += ['test']").code[0]
 +      vardef.should be_a(Puppet::Parser::AST::VarDef)
 +      vardef.append.should == true
      end
  
    end
@@@ -86,21 -84,21 +86,21 @@@
  
    describe "when parsing 'if'" do
      it "not, it should create the correct ast objects" do
 -      ast::Not.expects(:new).with { |h| h[:value].is_a?(ast::Boolean) }
 +      Puppet::Parser::AST::Not.expects(:new).with { |h| h[:value].is_a?(Puppet::Parser::AST::Boolean) }
        @parser.parse("if ! true { $var = 1 }")
      end
  
      it "boolean operation, it should create the correct ast objects" do
 -      ast::BooleanOperator.expects(:new).with {
 -        |h| h[:rval].is_a?(ast::Boolean) and h[:lval].is_a?(ast::Boolean) and h[:operator]=="or"
 +      Puppet::Parser::AST::BooleanOperator.expects(:new).with {
 +        |h| h[:rval].is_a?(Puppet::Parser::AST::Boolean) and h[:lval].is_a?(Puppet::Parser::AST::Boolean) and h[:operator]=="or"
        }
        @parser.parse("if true or true { $var = 1 }")
  
      end
  
      it "comparison operation, it should create the correct ast objects" do
 -      ast::ComparisonOperator.expects(:new).with {
 -        |h| h[:lval].is_a?(ast::Name) and h[:rval].is_a?(ast::Name) and h[:operator]=="<"
 +      Puppet::Parser::AST::ComparisonOperator.expects(:new).with {
 +        |h| h[:lval].is_a?(Puppet::Parser::AST::Name) and h[:rval].is_a?(Puppet::Parser::AST::Name) and h[:operator]=="<"
        }
        @parser.parse("if 1 < 2 { $var = 1 }")
  
@@@ -111,13 -109,13 +111,13 @@@
    describe "when parsing if complex expressions" do
      it "should create a correct ast tree" do
        aststub = stub_everything 'ast'
 -      ast::ComparisonOperator.expects(:new).with {
 -        |h| h[:rval].is_a?(ast::Name) and h[:lval].is_a?(ast::Name) and h[:operator]==">"
 +      Puppet::Parser::AST::ComparisonOperator.expects(:new).with {
 +        |h| h[:rval].is_a?(Puppet::Parser::AST::Name) and h[:lval].is_a?(Puppet::Parser::AST::Name) and h[:operator]==">"
        }.returns(aststub)
 -      ast::ComparisonOperator.expects(:new).with {
 -        |h| h[:rval].is_a?(ast::Name) and h[:lval].is_a?(ast::Name) and h[:operator]=="=="
 +      Puppet::Parser::AST::ComparisonOperator.expects(:new).with {
 +        |h| h[:rval].is_a?(Puppet::Parser::AST::Name) and h[:lval].is_a?(Puppet::Parser::AST::Name) and h[:operator]=="=="
        }.returns(aststub)
 -      ast::BooleanOperator.expects(:new).with {
 +      Puppet::Parser::AST::BooleanOperator.expects(:new).with {
          |h| h[:rval]==aststub and h[:lval]==aststub and h[:operator]=="and"
        }
        @parser.parse("if (1 > 2) and (1 == 2) { $var = 1 }")
@@@ -140,8 -138,9 +140,8 @@@
      end
  
      it "should create an ast::ResourceReference" do
 -      ast::Resource.stubs(:new)
 -      ast::ResourceReference.expects(:new).with { |arg|
 -        arg[:line]==1 and arg[:type]=="File" and arg[:title].is_a?(ast::ASTArray)
 +      Puppet::Parser::AST::ResourceReference.expects(:new).with { |arg|
 +        arg[:line]==1 and arg[:type]=="File" and arg[:title].is_a?(Puppet::Parser::AST::ASTArray)
        }
        @parser.parse('exec { test: command => File["a","b"] }')
      end
@@@ -158,14 -157,10 +158,14 @@@
      end
  
      it "should create an ast::ResourceOverride" do
 -      ast::ResourceOverride.expects(:new).with { |arg|
 -        arg[:line]==1 and arg[:object].is_a?(ast::ResourceReference) and arg[:parameters].is_a?(ast::ResourceParam)
 -      }
 -      @parser.parse('Resource["title1","title2"] { param => value }')
 +      #Puppet::Parser::AST::ResourceOverride.expects(:new).with { |arg|
 +      #  arg[:line]==1 and arg[:object].is_a?(Puppet::Parser::AST::ResourceReference) and arg[:parameters].is_a?(Puppet::Parser::AST::ResourceParam)
 +      #}
 +      ro = @parser.parse('Resource["title1","title2"] { param => value }').code[0]
 +      ro.should be_a(Puppet::Parser::AST::ResourceOverride)
 +      ro.line.should == 1
 +      ro.object.should be_a(Puppet::Parser::AST::ResourceReference)
 +      ro.parameters[0].should be_a(Puppet::Parser::AST::ResourceParam)
      end
  
    end
@@@ -185,17 -180,17 +185,17 @@@
      end
  
      it "should create a nop node for empty branch" do
 -      ast::Nop.expects(:new)
 +      Puppet::Parser::AST::Nop.expects(:new)
        @parser.parse("if true { }")
      end
  
      it "should create a nop node for empty else branch" do
 -      ast::Nop.expects(:new)
 +      Puppet::Parser::AST::Nop.expects(:new)
        @parser.parse("if true { notice('test') } else { }")
      end
  
      it "should build a chain of 'ifs' if there's an 'elsif'" do
 -      ast = @parser.parse(<<-PP)
 +      lambda { @parser.parse(<<-PP) }.should_not raise_error
          if true { notice('test') } elsif true {} else { }
        PP
      end
@@@ -264,7 -259,7 +264,7 @@@
      before do
        @lexer = stub 'lexer', :line => 50, :file => "/foo/bar", :getcomment => "whev"
        @parser.stubs(:lexer).returns @lexer
-       @class = stub 'class', :use_docs => false
+       @class = Puppet::Resource::Type.new(:hostclass, "myclass", :use_docs => false)
      end
  
      it "should return a new instance of the provided class created with the provided options" do
@@@ -299,6 -294,51 +299,6 @@@
      end
    end
  
 -  describe "when creating a node" do
 -    before :each do
 -      @lexer = stub 'lexer'
 -      @lexer.stubs(:getcomment)
 -      @parser.stubs(:lexer).returns(@lexer)
 -      @node = stub_everything 'node'
 -      @parser.stubs(:ast_context).returns({})
 -      @parser.stubs(:node).returns(nil)
 -
 -      @nodename = stub 'nodename', :is_a? => false, :value => "foo"
 -      @nodename.stubs(:is_a?).with(Puppet::Parser::AST::HostName).returns(true)
 -    end
 -
 -    it "should return an array of nodes" do
 -      @parser.newnode(@nodename).should be_instance_of(Array)
 -    end
 -
 -    it "should initialize the ast context with the correct line number" do
 -      @parser.expects(:ast_context).with { |a,b| b == 123 }.returns({})
 -      @parser.newnode(@nodename, { :line => 123 })
 -    end
 -  end
 -
 -  %w{class define}.each do |entity|
 -    describe "when creating a #{entity}" do
 -      before :each do
 -        @parser.stubs(:ast_context).returns({})
 -
 -        @name = stub "#{entity}name", :is_a? => false, :value => "foo"
 -      end
 -
 -      it "should create and add the correct resource type" do
 -        instance = stub 'instance'
 -        Puppet::Resource::Type.expects(:new).returns(instance)
 -        @parser.known_resource_types.expects(:add).with(instance)
 -        @parser.send("new#{entity}", @name)
 -      end
 -
 -      it "should initialize the ast context with the correct line number" do
 -        @parser.expects(:ast_context).with { |a,b| b == 123 }.returns({})
 -        @parser.send("new#{entity}", @name, { :line => 123 })
 -      end
 -    end
 -  end
 -
    describe "when retrieving a specific node" do
      it "should delegate to the known_resource_types node" do
        @known_resource_types.expects(:node).with("node")
@@@ -351,28 -391,30 +351,28 @@@
        @parser.stubs(:known_resource_types).returns @krt
      end
  
 -    it "should create new classes" do
 -      @parser.parse("class foobar {}")
 -      @krt.hostclass("foobar").should be_instance_of(Puppet::Resource::Type)
 +    it "should not create new classes" do
 +      @parser.parse("class foobar {}").code[0].should be_a(Puppet::Parser::AST::Hostclass)
 +      @krt.hostclass("foobar").should be_nil
      end
  
      it "should correctly set the parent class when one is provided" do
 -      @parser.parse("class foobar inherits yayness {}")
 -      @krt.hostclass("foobar").parent.should == "yayness"
 +      @parser.parse("class foobar inherits yayness {}").code[0].instantiate('')[0].parent.should == "yayness"
      end
  
      it "should correctly set the parent class for multiple classes at a time" do
 -      @parser.parse("class foobar inherits yayness {}\nclass boo inherits bar {}")
 -      @krt.hostclass("foobar").parent.should == "yayness"
 -      @krt.hostclass("boo").parent.should == "bar"
 +      statements = @parser.parse("class foobar inherits yayness {}\nclass boo inherits bar {}").code
 +      statements[0].instantiate('')[0].parent.should == "yayness"
 +      statements[1].instantiate('')[0].parent.should == "bar"
      end
  
      it "should define the code when some is provided" do
 -      @parser.parse("class foobar { $var = val }")
 -      @krt.hostclass("foobar").code.should_not be_nil
 +      @parser.parse("class foobar { $var = val }").code[0].code.should_not be_nil
      end
  
      it "should define parameters when provided" do
 -      @parser.parse("class foobar($biz,$baz) {}")
 -      @krt.hostclass("foobar").arguments.should == {"biz" => nil, "baz" => nil}
 +      foobar = @parser.parse("class foobar($biz,$baz) {}").code[0].instantiate('')[0]
 +      foobar.arguments.should == {"biz" => nil, "baz" => nil}
      end
    end
  
@@@ -389,37 -431,13 +389,37 @@@
      end
  
      it "should correctly mark exported resources as exported" do
 -      @parser.parse("@@file { '/file': }")
 -      @krt.hostclass("").code[0].exported.should be_true
 +      @parser.parse("@@file { '/file': }").code[0].exported.should be_true
      end
  
      it "should correctly mark virtual resources as virtual" do
 -      @parser.parse("@file { '/file': }")
 -      @krt.hostclass("").code[0].virtual.should be_true
 +      @parser.parse("@file { '/file': }").code[0].virtual.should be_true
 +    end
 +  end
 +
 +  describe "when parsing nodes" do
 +    it "should be able to parse a node with a single name" do
 +      node = @parser.parse("node foo { }").code[0]
 +      node.should be_a Puppet::Parser::AST::Node
 +      node.names.length.should == 1
 +      node.names[0].value.should == "foo"
 +    end
 +
 +    it "should be able to parse a node with two names" do
 +      node = @parser.parse("node foo, bar { }").code[0]
 +      node.should be_a Puppet::Parser::AST::Node
 +      node.names.length.should == 2
 +      node.names[0].value.should == "foo"
 +      node.names[1].value.should == "bar"
 +    end
 +
 +    it "should be able to parse a node with three names" do
 +      node = @parser.parse("node foo, bar, baz { }").code[0]
 +      node.should be_a Puppet::Parser::AST::Node
 +      node.names.length.should == 3
 +      node.names[0].value.should == "foo"
 +      node.names[1].value.should == "bar"
 +      node.names[2].value.should == "baz"
      end
    end
  end
diff --combined spec/unit/provider/ssh_authorized_key/parsed_spec.rb
index 7a1bd77,2e5be16..3ac57fa
--- a/spec/unit/provider/ssh_authorized_key/parsed_spec.rb
+++ b/spec/unit/provider/ssh_authorized_key/parsed_spec.rb
@@@ -1,13 -1,19 +1,13 @@@
  #!/usr/bin/env ruby
  
 -require File.dirname(__FILE__) + '/../../../spec_helper'
 -
 +require File.expand_path(File.dirname(__FILE__) + '/../../../spec_helper')
 +require 'shared_behaviours/all_parsedfile_providers'
  require 'puppet_spec/files'
 -require 'puppettest/support/utils'
 -require 'puppettest/fileparsing'
 -require 'puppettest/fakes'
  
  provider_class = Puppet::Type.type(:ssh_authorized_key).provider(:parsed)
  
  describe provider_class do
    include PuppetSpec::Files
 -  extend PuppetTest::Support::Utils
 -  include PuppetTest
 -  include PuppetTest::FileParsing
  
    before :each do
      @sshauthkey_class = Puppet::Type.type(:ssh_authorized_key)
@@@ -23,13 -29,15 +23,13 @@@
    end
  
    def mkkey(args)
 -    fakeresource = fakeresource(:ssh_authorized_key, args[:name])
 -    fakeresource.stubs(:should).with(:user).returns @user
 -    fakeresource.stubs(:should).with(:target).returns @keyfile
 -
 -    key = @provider.new(fakeresource)
 +    args[:target] = @keyfile
 +    args[:user]   = @user
 +    resource = Puppet::Type.type(:ssh_authorized_key).new(args)
 +    key = @provider.new(resource)
      args.each do |p,v|
        key.send(p.to_s + "=", v)
      end
 -
      key
    end
  
@@@ -42,28 -50,38 +42,28 @@@
      @provider.target_object(@keyfile).read
    end
  
 -  fakedata("data/providers/ssh_authorized_key/parsed").each { |file|
 -    it "should be able to parse example data in #{file}" do
 -      fakedataparse(file)
 -    end
 -  }
 +  it_should_behave_like "all parsedfile providers", provider_class
  
    it "should be able to generate a basic authorized_keys file" do
  
 -    key = mkkey(
 -      {
 -        :name => "Just Testing",
 -        :key => "AAAAfsfddsjldjgksdflgkjsfdlgkj",
 -        :type => "ssh-dss",
 -        :ensure => :present,
 -
 -        :options => [:absent]
 -    })
 +    key = mkkey(:name    => "Just Testing",
 +                :key     => "AAAAfsfddsjldjgksdflgkjsfdlgkj",
 +                :type    => "ssh-dss",
 +                :ensure  => :present,
 +                :options => [:absent]
 +              )
  
      genkey(key).should == "ssh-dss AAAAfsfddsjldjgksdflgkjsfdlgkj Just Testing\n"
    end
  
    it "should be able to generate a authorized_keys file with options" do
  
 -    key = mkkey(
 -      {
 -        :name => "root at localhost",
 -        :key => "AAAAfsfddsjldjgksdflgkjsfdlgkj",
 -        :type => "ssh-rsa",
 -        :ensure => :present,
 -
 -        :options => ['from="192.168.1.1"', "no-pty", "no-X11-forwarding"]
 -    })
 +    key = mkkey(:name    => "root at localhost",
 +                :key     => "AAAAfsfddsjldjgksdflgkjsfdlgkj",
 +                :type    => "ssh-rsa",
 +                :ensure  => :present,
 +                :options => ['from="192.168.1.1"', "no-pty", "no-X11-forwarding"]
 +                )
  
      genkey(key).should == "from=\"192.168.1.1\",no-pty,no-X11-forwarding ssh-rsa AAAAfsfddsjldjgksdflgkjsfdlgkj root at localhost\n"
    end
@@@ -86,6 -104,7 +86,7 @@@ describe provider_class d
    before :each do
      @resource = stub("resource", :name => "foo")
      @resource.stubs(:[]).returns "foo"
+     @resource.class.stubs(:key_attributes).returns( [:name] )
  
      @provider = provider_class.new(@resource)
      provider_class.stubs(:filetype).returns(Puppet::Util::FileType::FileTypeRam)
diff --combined spec/unit/provider/user/user_role_add_spec.rb
index 9cd0feb,f739423..12a71d2
--- a/spec/unit/provider/user/user_role_add_spec.rb
+++ b/spec/unit/provider/user/user_role_add_spec.rb
@@@ -1,6 -1,6 +1,6 @@@
  #!/usr/bin/env ruby
  
 -require File.dirname(__FILE__) + '/../../../spec_helper'
 +require File.expand_path(File.dirname(__FILE__) + '/../../../spec_helper')
  
  provider_class = Puppet::Type.type(:user).provider(:user_role_add)
  
@@@ -115,6 -115,7 +115,7 @@@ describe provider_class d
    describe "when allow duplicate is enabled" do
      before do
        @resource.expects(:allowdupe?).returns true
+       @resource.stubs(:system?)
        @provider.stubs(:is_role?).returns(false)
        @provider.stubs(:execute)
        @provider.expects(:execute).with { |args| args.include?("-o") }
diff --combined spec/unit/provider/user/useradd_spec.rb
index f9babe6,fd75c43..b1719ee
--- a/spec/unit/provider/user/useradd_spec.rb
+++ b/spec/unit/provider/user/useradd_spec.rb
@@@ -1,6 -1,6 +1,6 @@@
  #!/usr/bin/env ruby
  
 -require File.dirname(__FILE__) + '/../../../spec_helper'
 +require File.expand_path(File.dirname(__FILE__) + '/../../../spec_helper')
  
  provider_class = Puppet::Type.type(:user).provider(:useradd)
  
@@@ -15,6 -15,7 +15,7 @@@ describe provider_class d
    # #1360
    it "should add -o when allowdupe is enabled and the user is being created" do
      @resource.expects(:allowdupe?).returns true
+     @resource.expects(:system?).returns true
      @provider.stubs(:execute)
      @provider.expects(:execute).with { |args| args.include?("-o") }
      @provider.create
@@@ -27,6 -28,14 +28,14 @@@
      @provider.uid = 150
    end
  
+   it "should add -r when system is enabled" do
+     @resource.expects(:allowdupe?).returns true
+     @resource.expects(:system?).returns true
+     @provider.stubs(:execute)
+     @provider.expects(:execute).with { |args| args.include?("-r") }
+     @provider.create
+   end
+ 
    it "should set password age rules" do
      provider_class.has_feature :manages_password_age
      @resource = Puppet::Type.type(:user).new :name => "myuser", :password_min_age => 5, :password_max_age => 10, :provider => :useradd
@@@ -53,6 -62,23 +62,23 @@@
      end
    end
  
+   describe "when checking to add system users" do
+     it "should check system users" do
+       @resource.expects(:system?)
+       @provider.check_system_users
+     end
+ 
+     it "should return an array with a flag if it's a system user" do
+       @resource.stubs(:system?).returns true
+       @provider.check_system_users.must == ["-r"]
+     end
+ 
+     it "should return an empty array if it's not a system user" do
+       @resource.stubs(:system?).returns false
+       @provider.check_system_users.must == []
+     end
+   end
+ 
    describe "when checking manage home" do
      it "should check manage home" do
        @resource.expects(:managehome?)
@@@ -88,6 -114,7 +114,7 @@@
      before do
        @resource.stubs(:allowdupe?).returns true
        @resource.stubs(:managehome?).returns true
+       @resource.stubs(:system?).returns true
      end
  
      it "should call command with :add" do
@@@ -115,20 -142,32 +142,32 @@@
        @provider.addcmd
      end
  
+     it "should return an array with -r if system? is true" do
+       resource = Puppet::Type.type(:user).new( :name => "bob", :system => true)
+ 
+       provider_class.new( resource ).addcmd.should include("-r")
+     end
+ 
+     it "should return an array without -r if system? is false" do
+       resource = Puppet::Type.type(:user).new( :name => "bob", :system => false)
+ 
+       provider_class.new( resource ).addcmd.should_not include("-r")
+     end
+ 
      it "should return an array with full command" do
        @provider.stubs(:command).with(:add).returns("useradd")
        @provider.stubs(:add_properties).returns(["-G", "somegroup"])
        @resource.stubs(:[]).with(:name).returns("someuser")
        @resource.stubs(:[]).with(:expiry).returns("somedate")
-       @provider.addcmd.must == ["useradd", "-G", "somegroup", "-o", "-m", '-e somedate', "someuser"]
+       @provider.addcmd.must == ["useradd", "-G", "somegroup", "-o", "-m", '-e somedate', "-r", "someuser"]
      end
  
-     it "should return an array without -e if expery is undefined full command" do
+     it "should return an array without -e if expiry is undefined full command" do
        @provider.stubs(:command).with(:add).returns("useradd")
        @provider.stubs(:add_properties).returns(["-G", "somegroup"])
        @resource.stubs(:[]).with(:name).returns("someuser")
        @resource.stubs(:[]).with(:expiry).returns nil
-       @provider.addcmd.must == ["useradd", "-G", "somegroup", "-o", "-m", "someuser"]
+       @provider.addcmd.must == ["useradd", "-G", "somegroup", "-o", "-m", "-r", "someuser"]
      end
    end
  
@@@ -136,6 -175,7 +175,7 @@@
      before do
        @resource.stubs(:allowdupe?).returns true
        @resource.stubs(:managehome?).returns true
+       @resource.stubs(:system?).returns true
      end
  
      it "should call command with :pass" do
diff --combined spec/unit/resource_spec.rb
index e5146f3,345ccd0..916741d
--- a/spec/unit/resource_spec.rb
+++ b/spec/unit/resource_spec.rb
@@@ -1,6 -1,6 +1,6 @@@
  #!/usr/bin/env ruby
  
 -require File.dirname(__FILE__) + '/../spec_helper'
 +require File.expand_path(File.dirname(__FILE__) + '/../spec_helper')
  require 'puppet/resource'
  
  describe Puppet::Resource do
@@@ -463,6 -463,28 +463,28 @@@
      end
    end
  
+   describe "when loading 0.25.x storedconfigs YAML" do
+     before :each do
+       @old_storedconfig_yaml = %q{--- !ruby/object:Puppet::Resource::Reference
+ builtin_type:
+ title: /tmp/bar
+ type: File
+ }
+     end
+ 
+     it "should deserialize a Puppet::Resource::Reference without exceptions" do
+       lambda { YAML.load(@old_storedconfig_yaml) }.should_not raise_error
+     end
+ 
+     it "should deserialize as a Puppet::Resource::Reference as a Puppet::Resource" do
+       YAML.load(@old_storedconfig_yaml).class.should == Puppet::Resource
+     end
+ 
+     it "should to_hash properly" do
+       YAML.load(@old_storedconfig_yaml).to_hash.should == { :path => "/tmp/bar" }
+     end
+   end
+ 
    describe "when converting to a RAL resource" do
      it "should use the resource type's :new method to create the resource if the resource is of a builtin type" do
        resource = Puppet::Resource.new("file", @basepath+"/my/file")
diff --combined spec/unit/type/mount_spec.rb
index 333876c,fdb67f7..4638e9a
--- a/spec/unit/type/mount_spec.rb
+++ b/spec/unit/type/mount_spec.rb
@@@ -1,6 -1,6 +1,6 @@@
  #!/usr/bin/env ruby
  
 -require File.dirname(__FILE__) + '/../../spec_helper'
 +require File.expand_path(File.dirname(__FILE__) + '/../../spec_helper')
  
  describe Puppet::Type.type(:mount) do
    it "should have a :refreshable feature that requires the :remount method" do
@@@ -65,7 -65,8 +65,8 @@@ en
  
  describe Puppet::Type.type(:mount)::Ensure do
    before :each do
-     @provider = stub 'provider', :class => Puppet::Type.type(:mount).defaultprovider, :clear => nil, :satisfies? => true, :name => :mock
+     provider_properties = {}
+     @provider = stub 'provider', :class => Puppet::Type.type(:mount).defaultprovider, :clear => nil, :satisfies? => true, :name => :mock, :property_hash => provider_properties
      Puppet::Type.type(:mount).defaultprovider.stubs(:new).returns(@provider)
      @mount = Puppet::Type.type(:mount).new(:name => "yay", :check => :ensure)
  
@@@ -93,11 -94,12 +94,12 @@@
        @provider.stubs(:mounted?).returns([:mounted,:ghost].include? options[:from])
        @provider.expects(:create).times(options[:create] || 0)
        @provider.expects(:destroy).times(options[:destroy] || 0)
-       @provider.expects(:mount).times(options[:mount] || 0)
+       @provider.expects(:mount).never
        @provider.expects(:unmount).times(options[:unmount] || 0)
        @ensure.stubs(:syncothers)
        @ensure.should = options[:to]
        @ensure.sync
+       (!!@provider.property_hash[:needs_mount]).should == (!!options[:mount])
     end
  
     it "should create itself when changing from :ghost to :present" do
@@@ -229,49 -231,27 +231,51 @@@
  
   end
  
 -  describe Puppet::Type.type(:mount), "when responding to events" do
 +  describe Puppet::Type.type(:mount), "when responding to refresh" do
++    pending "2.6.x specifies slightly different behavior and the desired behavior needs to be clarified and revisited.  See ticket #4904" do
  
-     it "should remount if it is supposed to be mounted" do
-       @mount[:ensure] = "mounted"
-       @provider.expects(:remount)
 -    it "should remount if it is currently mounted" do
 -      @provider.expects(:mounted?).returns(true)
 -      @provider.expects(:remount)
++      it "should remount if it is supposed to be mounted" do
++        @mount[:ensure] = "mounted"
++        @provider.expects(:remount)
  
--      @mount.refresh
--    end
++        @mount.refresh
++      end
  
-     it "should not remount if it is supposed to be present" do
-       @mount[:ensure] = "present"
-       @provider.expects(:remount).never
 -    it "should not remount if it is not currently mounted" do
 -      @provider.expects(:mounted?).returns(false)
 -      @provider.expects(:remount).never
++      it "should not remount if it is supposed to be present" do
++        @mount[:ensure] = "present"
++        @provider.expects(:remount).never
  
--      @mount.refresh
--    end
++        @mount.refresh
++      end
 +
-     it "should not remount if it is supposed to be absent" do
-       @mount[:ensure] = "absent"
-       @provider.expects(:remount).never
++      it "should not remount if it is supposed to be absent" do
++        @mount[:ensure] = "absent"
++        @provider.expects(:remount).never
 +
-       @mount.refresh
-     end
++        @mount.refresh
++      end
  
-     it "should not remount if it is supposed to be defined" do
-       @mount[:ensure] = "defined"
-       @provider.expects(:remount).never
 -    it "should not remount swap filesystems" do
 -      @mount[:fstype] = "swap"
 -      @provider.expects(:remount).never
++      it "should not remount if it is supposed to be defined" do
++        @mount[:ensure] = "defined"
++        @provider.expects(:remount).never
  
--      @mount.refresh
-     end
++        @mount.refresh
++      end
 +
-     it "should not remount if it is supposed to be unmounted" do
-       @mount[:ensure] = "unmounted"
-       @provider.expects(:remount).never
++      it "should not remount if it is supposed to be unmounted" do
++        @mount[:ensure] = "unmounted"
++        @provider.expects(:remount).never
 +
-       @mount.refresh
-     end
++        @mount.refresh
++      end
 +
-     it "should not remount swap filesystems" do
-       @mount[:ensure] = "mounted"
-       @mount[:fstype] = "swap"
-       @provider.expects(:remount).never
++      it "should not remount swap filesystems" do
++        @mount[:ensure] = "mounted"
++        @mount[:fstype] = "swap"
++        @provider.expects(:remount).never
 +
-       @mount.refresh
++        @mount.refresh
++      end
      end
    end
  end
@@@ -307,34 -287,6 +311,6 @@@ describe Puppet::Type.type(:mount), "wh
      @catalog.apply
    end
  
-   it "should flush changes before mounting" do
-     syncorder = sequence('syncorder')
-     @mount.provider.expects(:options).returns 'soft'
-     @mount.provider.expects(:ensure).returns :unmounted
-     @mount.provider.expects(:mounted?).returns false
- 
-     @mount.provider.expects(:options=).in_sequence(syncorder).with 'hard'
-     @mount.expects(:flush).in_sequence(syncorder) # Have to write with no options
-     @mount.provider.expects(:mount).in_sequence(syncorder)
-     @mount.expects(:flush).in_sequence(syncorder) # Call flush again cause we changed everything
- 
-     @mount[:ensure] = :mounted
-     @mount[:options] = 'hard'
- 
-     @catalog.apply
-   end
- 
-   it "should not flush before mounting if there are no other changes" do
-     syncorder = sequence('syncorder')
-     @mount.provider.expects(:ensure).returns :unmounted
-     @mount.provider.expects(:mounted?).returns false
-     @mount.provider.expects(:mount).in_sequence(syncorder)
-     @mount.expects(:flush).in_sequence(syncorder) # Call flush cause we changed everything
- 
-     @mount[:ensure] = :mounted
-     @catalog.apply
-   end
- 
    it "should umount before flushing changes to disk" do
      syncorder = sequence('syncorder')
      @mount.provider.expects(:options).returns 'soft'
diff --combined spec/unit/type/user_spec.rb
index 117c90f,5a84af4..6421e60
--- a/spec/unit/type/user_spec.rb
+++ b/spec/unit/type/user_spec.rb
@@@ -1,6 -1,6 +1,6 @@@
  #!/usr/bin/env ruby
  
 -require File.dirname(__FILE__) + '/../../spec_helper'
 +require File.expand_path(File.dirname(__FILE__) + '/../../spec_helper')
  
  user = Puppet::Type.type(:user)
  
@@@ -43,6 -43,10 +43,10 @@@ describe user d
      user.provider_feature(:manages_password_age).should_not be_nil
    end
  
+   it "should have a system_users feature" do
+     user.provider_feature(:system_users).should_not be_nil
+   end
+ 
    describe "instances" do
      it "should have a valid provider" do
        user.new(:name => "foo").provider.class.ancestors.should be_include(Puppet::Provider)
diff --combined spec/unit/type_spec.rb
index d1143d9,6d9d0b2..f9372fc
--- a/spec/unit/type_spec.rb
+++ b/spec/unit/type_spec.rb
@@@ -1,6 -1,6 +1,6 @@@
  #!/usr/bin/env ruby
  
 -require File.dirname(__FILE__) + '/../spec_helper'
 +require File.expand_path(File.dirname(__FILE__) + '/../spec_helper')
  
  describe Puppet::Type do
    it "should include the Cacher module" do
@@@ -434,7 -434,7 +434,7 @@@
          patterns.length.should == 1
          patterns[0].length.should == 2
        end
-       
+ 
        it "should have a regexp that captures the entire string" do
          patterns = @type_class.title_patterns
          string = "abc\n\tdef"
@@@ -570,4 -570,15 +570,15 @@@ describe Puppet::Type.metaparamclass(:a
      @resource[:audit] = :noop
      @resource.parameter(:noop).should be_nil
    end
+ 
+   describe "when generating the uniqueness key" do
+     it "should include all of the key_attributes in alphabetical order by attribute name" do
+       Puppet::Type.type(:file).stubs(:key_attributes).returns [:path, :mode, :owner]
+       Puppet::Type.type(:file).stubs(:title_patterns).returns(
+         [ [ /(.*)/, [ [:path, lambda{|x| x} ] ] ] ]
+       )
+       res = Puppet::Type.type(:file).new( :title => '/my/file', :path => '/my/file', :owner => 'root', :content => 'hello' )
+       res.uniqueness_key.should == [ nil, 'root', '/my/file']
+     end
+   end
  end
diff --combined spec/unit/util/settings_spec.rb
index 732be6a,07b712c..2ab31c2
--- a/spec/unit/util/settings_spec.rb
+++ b/spec/unit/util/settings_spec.rb
@@@ -1,6 -1,6 +1,6 @@@
  #!/usr/bin/env ruby
  
 -require File.dirname(__FILE__) + '/../../spec_helper'
 +require File.expand_path(File.dirname(__FILE__) + '/../../spec_helper')
  
  describe Puppet::Util::Settings do
    describe "when specifying defaults" do
@@@ -284,7 -284,8 +284,8 @@@
        @settings = Puppet::Util::Settings.new
        @settings.setdefaults :section,
          :config => ["/my/file", "a"],
-         :one => ["ONE", "a"]
+         :one => ["ONE", "a"],
+         :two => ["TWO", "b"]
        FileTest.stubs(:exist?).returns true
        Puppet.stubs(:run_mode).returns stub('run_mode', :name => :mymode)
      end
@@@ -331,12 -332,20 +332,20 @@@
        @settings.value(:one, "env").should == "envval"
      end
  
-     it "should interpolate found values using the current environment" do
+     it 'should use the current environment for $environment' do
        @settings.setdefaults :main, :myval => ["$environment/foo", "mydocs"]
  
        @settings.value(:myval, "myenv").should == "myenv/foo"
      end
  
+     it "should interpolate found values using the current environment" do
+       text = "[main]\none = mainval\n[myname]\none = nameval\ntwo = $one/two\n"
+       @settings.stubs(:read_file).returns(text)
+       @settings.parse
+ 
+       @settings.value(:two, "myname").should == "nameval/two"
+     end
+ 
      it "should return values in a specified environment before values in the main or name sections" do
        text = "[env]\none = envval\n[main]\none = mainval\n[myname]\none = nameval\n"
        @settings.stubs(:read_file).returns(text)

-- 
Puppet packaging for Debian



More information about the Pkg-puppet-devel mailing list