summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--lib/puppet/parser/interpreter.rb4
-rw-r--r--lib/puppet/parser/resource.rb12
-rw-r--r--lib/puppet/parser/resource/param.rb25
-rw-r--r--lib/puppet/rails/host.rb74
-rw-r--r--lib/puppet/rails/param_name.rb3
-rw-r--r--lib/puppet/rails/resource.rb3
-rw-r--r--lib/puppet/util/rails/collection_merger.rb25
-rwxr-xr-xtest/language/ast.rb2
-rwxr-xr-xtest/language/interpreter.rb4
-rw-r--r--test/lib/puppettest/railstesting.rb2
-rwxr-xr-xtest/rails/host.rb136
-rwxr-xr-xtest/rails/rails.rb84
-rwxr-xr-xtest/rails/railsresource.rb4
13 files changed, 216 insertions, 162 deletions
diff --git a/lib/puppet/parser/interpreter.rb b/lib/puppet/parser/interpreter.rb
index 5fe50d144..5144c4970 100644
--- a/lib/puppet/parser/interpreter.rb
+++ b/lib/puppet/parser/interpreter.rb
@@ -143,7 +143,7 @@ class Puppet::Parser::Interpreter
scope.name = "top"
scope.type = "main"
- scope.host = client
+ scope.host = client || facts["hostname"] || Facter.value(:hostname)
classes = @classes.dup
@@ -192,7 +192,7 @@ class Puppet::Parser::Interpreter
if Puppet[:storeconfigs]
args = {
:resources => scope.resources,
- :name => client,
+ :name => scope.host,
:facts => facts
}
unless scope.classlist.empty?
diff --git a/lib/puppet/parser/resource.rb b/lib/puppet/parser/resource.rb
index 857b5fa39..05e0af4c1 100644
--- a/lib/puppet/parser/resource.rb
+++ b/lib/puppet/parser/resource.rb
@@ -279,18 +279,8 @@ class Puppet::Parser::Resource
end
# Either way, now add our parameters
- exists = {}
- obj.param_names.each do |pn| exists[pn.name] = pn end
- @params.each do |name, param|
+ obj.collection_merge(:param_names, @params) do |name, param|
param.to_rails(obj)
- exists.delete(name.to_s) if exists.include?(name.to_s)
- end
-
- unless exists.empty?
- obj.save
- exists.each do |name, param|
- obj.param_names.delete(param)
- end
end
return obj
diff --git a/lib/puppet/parser/resource/param.rb b/lib/puppet/parser/resource/param.rb
index 6f24f1486..1f7a66aae 100644
--- a/lib/puppet/parser/resource/param.rb
+++ b/lib/puppet/parser/resource/param.rb
@@ -23,31 +23,18 @@ class Puppet::Parser::Resource::Param
# We're creating it anew.
pn = res.param_names.build(:name => self.name.to_s)
end
+
+ value_objects = []
if l = self.line
pn.line = Integer(l)
end
- exists = {}
- pn.param_values.each { |pv| exists[pv.value] = pv }
- values.each do |value|
- unless pn.param_values.find_by_value(value)
- pn.param_values.build(:value => value)
- end
- # Mark that this is still valid.
- if exists.include?(value)
- exists.delete(value)
- end
- end
-
- # And remove any existing values that are not in the current value list.
- unless exists.empty?
- # We have to save the current state else the deletion somehow deletes
- # our new values.
- pn.save
- exists.each do |value, obj|
- pn.param_values.delete(obj)
+ pn.collection_merge(:param_values, values) do |value|
+ unless pv = pn.param_values.find_by_value(value)
+ pv = pn.param_values.build(:value => value)
end
+ pv
end
return pn
diff --git a/lib/puppet/rails/host.rb b/lib/puppet/rails/host.rb
index a46fa92a5..fcd078cb7 100644
--- a/lib/puppet/rails/host.rb
+++ b/lib/puppet/rails/host.rb
@@ -1,6 +1,9 @@
require 'puppet/rails/resource'
+require 'puppet/util/rails/collection_merger'
class Puppet::Rails::Host < ActiveRecord::Base
+ include Puppet::Util::CollectionMerger
+
has_many :fact_values, :through => :fact_names
has_many :fact_names, :dependent => :destroy
belongs_to :puppet_classes
@@ -11,14 +14,6 @@ class Puppet::Rails::Host < ActiveRecord::Base
acts_as_taggable
- def facts(name)
- if fv = self.fact_values.find(:first, :conditions => "fact_names.name = '#{name}'")
- return fv.value
- else
- return nil
- end
- end
-
# If the host already exists, get rid of its objects
def self.clean(host)
if obj = self.find_by_name(host)
@@ -31,60 +26,59 @@ class Puppet::Rails::Host < ActiveRecord::Base
# Store our host in the database.
def self.store(hash)
- unless hash[:name]
+ unless name = hash[:name]
raise ArgumentError, "You must specify the hostname for storage"
end
args = {}
- if hash[:facts].include?("ipaddress")
- args[:ip] = hash[:facts]["ipaddress"]
+ unless host = find_by_name(name)
+ host = new(:name => name)
end
- unless host = find_by_name(hash[:facts]["hostname"])
- host = new(:name => hash[:facts]["hostname"])
+ if ip = hash[:facts]["ipaddress"]
+ host.ip = ip
end
- # Store the facts into the
- hash[:facts].each do |name, value|
- fn = host.fact_names.find_by_name(name) || host.fact_names.build(:name => name)
- unless fn.fact_values.find_by_value(value)
- fn.fact_values.build(:value => value)
- end
- end
+ # Store the facts into the database.
+ host.setfacts(hash[:facts])
unless hash[:resources]
raise ArgumentError, "You must pass resources"
end
- resources = []
- hash[:resources].each do |resource|
- resources << resource.to_rails(host)
- end
+ host.setresources(hash[:resources])
host.save
return host
end
- # Add all of our RailsObjects
- def addobjects(objects)
- objects.each do |tobj|
- params = {}
- tobj.each do |p,v| params[p] = v end
-
- args = {:ptype => tobj.type, :name => tobj.name}
- [:tags, :file, :line].each do |param|
- if val = tobj.send(param)
- args[param] = val
- end
+ # Return the value of a fact.
+ def fact(name)
+ if fv = self.fact_values.find(:first, :conditions => "fact_names.name = '#{name}'")
+ return fv.value
+ else
+ return nil
+ end
+ end
+
+ def setfacts(facts)
+ collection_merge(:fact_names, facts) do |name, value|
+ fn = fact_names.find_by_name(name) || fact_names.build(:name => name)
+ # We're only ever going to have one fact value, at this point.
+ unless fv = fn.fact_values.find_by_value(value)
+ fv = fn.fact_values.build(:value => value)
end
+ fn.fact_values = [fv]
- robj = rails_objects.build(args)
+ fn
+ end
+ end
- robj.addparams(params)
- if tobj.collectable
- robj.toggle(:collectable)
- end
+ # Set our resources.
+ def setresources(list)
+ collection_merge(:resources, list) do |resource|
+ resource.to_rails(self)
end
end
end
diff --git a/lib/puppet/rails/param_name.rb b/lib/puppet/rails/param_name.rb
index dba6960da..b609f10c5 100644
--- a/lib/puppet/rails/param_name.rb
+++ b/lib/puppet/rails/param_name.rb
@@ -1,4 +1,7 @@
+require 'puppet/util/rails/collection_merger'
+
class Puppet::Rails::ParamName < ActiveRecord::Base
+ include Puppet::Util::CollectionMerger
has_many :param_values, :dependent => :destroy
belongs_to :resource
diff --git a/lib/puppet/rails/resource.rb b/lib/puppet/rails/resource.rb
index c0a7fbd8c..d78b02b88 100644
--- a/lib/puppet/rails/resource.rb
+++ b/lib/puppet/rails/resource.rb
@@ -1,8 +1,11 @@
require 'puppet'
require 'puppet/rails/lib/init'
require 'puppet/rails/param_name'
+require 'puppet/util/rails/collection_merger'
class Puppet::Rails::Resource < ActiveRecord::Base
+ include Puppet::Util::CollectionMerger
+
has_many :param_values, :through => :param_names
has_many :param_names, :dependent => :destroy
has_many :source_files
diff --git a/lib/puppet/util/rails/collection_merger.rb b/lib/puppet/util/rails/collection_merger.rb
new file mode 100644
index 000000000..7afd76f9c
--- /dev/null
+++ b/lib/puppet/util/rails/collection_merger.rb
@@ -0,0 +1,25 @@
+module Puppet::Util::CollectionMerger
+ # Merge new values with the old list. This is only necessary
+ # because deletion seems to mess things up on unsaved objects.
+ def collection_merge(collection, list)
+ remove = send(collection).dup
+
+ list.each do |value|
+ object = yield(value)
+ if remove.include?(object)
+ remove.delete(object)
+ end
+ end
+
+ unless remove.empty?
+ # We have to save the current state else the deletion somehow deletes
+ # our new values.
+ save
+ remove.each do |r|
+ send(collection).delete(r)
+ end
+ end
+ end
+end
+
+# $Id$
diff --git a/test/language/ast.rb b/test/language/ast.rb
index 733ca4b36..d42ac7936 100755
--- a/test/language/ast.rb
+++ b/test/language/ast.rb
@@ -498,7 +498,7 @@ class TestAST < Test::Unit::TestCase
# Not sure this is correct, maybe we need a case statement to convert to/from
# the autogenerated Puppet<Type> classes to <type>
- assert_equal(PuppetFile, res.class)
+ assert_equal("file", res.restype)
assert_equal("/tmp/testing", res.title)
else
assert_equal(0, retval.length, "found a resource with '#{string}'")
diff --git a/test/language/interpreter.rb b/test/language/interpreter.rb
index 3e542acb4..a19bec288 100755
--- a/test/language/interpreter.rb
+++ b/test/language/interpreter.rb
@@ -898,7 +898,7 @@ class TestInterpreter < Test::Unit::TestCase
interp.evaluate("myhost", {})
# And then retrieve the object from rails
- res = Puppet::Rails::Resource.find_by_type_and_title("PuppetFile", "/tmp/yay")
+ res = Puppet::Rails::Resource.find_by_restype_and_title("file", "/tmp/yay")
assert(res, "Did not get resource from rails")
@@ -906,7 +906,7 @@ class TestInterpreter < Test::Unit::TestCase
assert(param, "Did not find owner param")
- pvalue = param.param_values.find_by_value("root")
+ pvalue = param.param_values.find_by_value("root")
assert_equal("root", pvalue[:value])
end
end
diff --git a/test/lib/puppettest/railstesting.rb b/test/lib/puppettest/railstesting.rb
index e2ce7ef3f..c8f55ead8 100644
--- a/test/lib/puppettest/railstesting.rb
+++ b/test/lib/puppettest/railstesting.rb
@@ -25,7 +25,7 @@ module PuppetTest::RailsTesting
# Now build a resource
resources = []
- resources << mkresource(:restype => type, :title => title, :exported => true,
+ resources << mkresource(:type => type, :title => title, :exported => true,
:params => params)
# Now collect our facts
diff --git a/test/rails/host.rb b/test/rails/host.rb
new file mode 100755
index 000000000..38389ac64
--- /dev/null
+++ b/test/rails/host.rb
@@ -0,0 +1,136 @@
+#!/usr/bin/env ruby
+
+$:.unshift("../lib").unshift("../../lib") if __FILE__ =~ /\.rb$/
+
+require 'puppet'
+require 'puppet/rails'
+require 'puppet/parser/interpreter'
+require 'puppet/parser/parser'
+require 'puppet/client'
+require 'puppettest'
+require 'puppettest/parsertesting'
+require 'puppettest/resourcetesting'
+require 'puppettest/railstesting'
+
+class TestRailsHost < Test::Unit::TestCase
+ include PuppetTest::ParserTesting
+ include PuppetTest::ResourceTesting
+ include PuppetTest::RailsTesting
+
+ def setup
+ super
+ railsinit
+ end
+
+ def teardown
+ railsteardown
+ super
+ end
+
+ def test_includerails
+ assert_nothing_raised {
+ require 'puppet/rails'
+ }
+ end
+
+ # Don't do any tests w/out this class
+ if Puppet.features.rails?
+ def test_store
+ @interp, @scope, @source = mkclassframing
+ # First make some objects
+ resources = []
+ 10.times { |i|
+ # Make a file
+ resources << mkresource(:type => "file",
+ :title => "/tmp/file#{i.to_s}",
+ :params => {:owner => "user#{i}"})
+
+ # And an exec, so we're checking multiple types
+ resources << mkresource(:type => "exec",
+ :title => "/bin/echo file#{i.to_s}",
+ :params => {:user => "user#{i}"})
+ }
+
+ # Now collect our facts
+ facts = {"hostname" => Facter.value(:hostname), "test1" => "funtest",
+ "ipaddress" => Facter.value(:ipaddress)}
+
+ # Now try storing our crap
+ host = nil
+ assert_nothing_raised {
+ host = Puppet::Rails::Host.store(
+ :resources => resources,
+ :facts => facts,
+ :name => facts["hostname"],
+ :classes => ["one", "two::three", "four"]
+ )
+ }
+
+ assert(host, "Did not create host")
+
+ host = nil
+ assert_nothing_raised {
+ host = Puppet::Rails::Host.find_by_name(facts["hostname"])
+ }
+ assert(host, "Could not find host object")
+
+ assert(host.resources, "No objects on host")
+
+ facts.each do |fact, value|
+ assert_equal(value, host.fact(fact), "fact %s is wrong" % fact)
+ end
+ assert_equal(facts["ipaddress"], host.ip, "IP did not get set")
+
+ count = 0
+ host.resources.each do |resource|
+ assert_equal(host, resource.host)
+ count += 1
+ i = nil
+ if resource[:title] =~ /file([0-9]+)/
+ i = $1
+ else
+ raise "Got weird resource %s" % resource.inspect
+ end
+ assert(resource[:restype] != "", "Did not get a type from the resource")
+ case resource["restype"]
+ when "file":
+ assert_equal("user#{i}", resource.parameter("owner"),
+ "got no owner for %s" % resource.ref)
+ when "exec":
+ assert_equal("user#{i}", resource.parameter("user"),
+ "got no user for %s" % resource.ref)
+ else
+ raise "Unknown type %s" % resource[:restype].inspect
+ end
+ end
+
+ assert_equal(20, count, "Did not get enough resources")
+
+ # Now remove a couple of resources and change a fact
+ resources.reject! { |r| r.title =~ /file9/ }
+ facts["test2"] = "yaytest"
+ facts.delete("test1")
+ host = nil
+ assert_nothing_raised {
+ host = Puppet::Rails::Host.store(
+ :resources => resources,
+ :facts => facts,
+ :name => facts["hostname"],
+ :classes => ["one", "two::three", "four"]
+ )
+ }
+
+ assert_nil(host.fact('test1'), "removed fact was not deleted")
+ facts.each do |fact, value|
+ assert_equal(value, host.fact(fact), "fact %s is wrong" % fact)
+ end
+
+ assert(! host.resources.find(:all).detect { |r| r.title =~ /file9/ },
+ "Removed resources are still present")
+ end
+ else
+ $stderr.puts "Install Rails for Rails and Caching tests"
+ end
+end
+
+# $Id$
diff --git a/test/rails/rails.rb b/test/rails/rails.rb
index 69e1fd7b8..c0f902d65 100755
--- a/test/rails/rails.rb
+++ b/test/rails/rails.rb
@@ -32,90 +32,6 @@ class TestRails < Test::Unit::TestCase
require 'puppet/rails'
}
end
-
- # Don't do any tests w/out this class
- if Puppet.features.rails?
- def test_hostcache
- @interp, @scope, @source = mkclassframing
- # First make some objects
- resources = []
- 10.times { |i|
- # Make a file
- resources << mkresource(:type => "file",
- :title => "/tmp/file#{i.to_s}",
- :params => {:owner => "user#{i}"})
-
- # And an exec, so we're checking multiple types
- resources << mkresource(:type => "exec",
- :title => "/bin/echo file#{i.to_s}",
- :params => {:user => "user#{i}"})
- }
-
- # Now collect our facts
- facts = {"hostname" => Facter.value(:hostname), "test1" => "funtest"}
-
- # Now try storing our crap
- host = nil
- assert_nothing_raised {
- host = Puppet::Rails::Host.store(
- :resources => resources,
- :facts => facts,
- :name => facts["hostname"],
- :classes => ["one", "two::three", "four"]
- )
- }
-
- assert(host, "Did not create host")
-
- host = nil
- assert_nothing_raised {
- host = Puppet::Rails::Host.find_by_name(facts["hostname"])
- }
- assert(host, "Could not find host object")
-
- assert(host.resources, "No objects on host")
-
- assert_equal(facts["hostname"], host.facts("hostname"),
- "Did not retrieve facts")
-
- count = 0
- host.resources.each do |resource|
- assert_equal(host, resource.host)
- count += 1
- i = nil
- if resource[:title] =~ /file([0-9]+)/
- i = $1
- else
- raise "Got weird resource %s" % resource.inspect
- end
- assert(resource[:restype] != "", "Did not get a type from the resource")
- case resource["restype"]
- when "file":
- assert_equal("user#{i}", resource.parameter("owner"),
- "got no owner for %s" % resource.ref)
- when "exec":
- assert_equal("user#{i}", resource.parameter("user"),
- "got no user for %s" % resource.ref)
- else
- raise "Unknown type %s" % resource[:restype].inspect
- end
- end
-
- assert_equal(20, count, "Did not get enough resources")
-
- host = nil
- assert_nothing_raised {
- host = Puppet::Rails::Host.store(
- :resources => resources,
- :facts => facts,
- :name => facts["hostname"],
- :classes => ["one", "two::three", "four"]
- )
- }
- end
- else
- $stderr.puts "Install Rails for Rails and Caching tests"
- end
end
# $Id$
diff --git a/test/rails/railsresource.rb b/test/rails/railsresource.rb
index 302dd99fb..968e0e1b9 100755
--- a/test/rails/railsresource.rb
+++ b/test/rails/railsresource.rb
@@ -66,8 +66,8 @@ class TestRailsResource < Test::Unit::TestCase
res = resource.to_resource(scope)
end
assert_instance_of(Puppet::Parser::Resource, res)
- assert_equal("root", res[:owner])
- assert_equal("644", res[:mode])
+ assert_equal(["root"], res[:owner])
+ assert_equal(["644"], res[:mode])
assert_equal("/tmp/to_resource", res.title)
assert_equal(source, res.source)
end