diff --git a/test/language/compile.rb b/test/language/compile.rb index 298493c0a..082b37a1c 100755 --- a/test/language/compile.rb +++ b/test/language/compile.rb @@ -1,569 +1,569 @@ #!/usr/bin/env ruby require File.dirname(__FILE__) + '/../lib/puppettest' require 'mocha' require 'puppettest' require 'puppettest/parsertesting' require 'puppet/parser/compile' # Test our compile object. class TestCompile < Test::Unit::TestCase include PuppetTest include PuppetTest::ParserTesting Compile = Puppet::Parser::Compile Scope = Puppet::Parser::Scope Node = Puppet::Network::Handler.handler(:node) SimpleNode = Puppet::Node def mknode(name = "foo") @node = SimpleNode.new(name) end def mkparser # This should mock an interpreter @parser = stub 'parser', :version => "1.0", :nodes => {} end def mkcompile(options = {}) if node = options[:node] options.delete(:node) else node = mknode end @compile = Compile.new(node, mkparser, options) end def test_initialize compile = nil node = stub 'node', :name => "foo" parser = stub 'parser', :version => "1.0", :nodes => {} assert_nothing_raised("Could not init compile with all required options") do compile = Compile.new(node, parser) end assert_equal(node, compile.node, "Did not set node correctly") assert_equal(parser, compile.parser, "Did not set parser correctly") # We're not testing here whether we call initvars, because it's too difficult to # mock. # Now try it with some options assert_nothing_raised("Could not init compile with extra options") do compile = Compile.new(node, parser) end assert_equal(false, compile.ast_nodes?, "Did not set ast_nodes? correctly") end def test_initvars compile = mkcompile [:class_scopes, :resource_table, :exported_resources, :resource_overrides].each do |table| assert_instance_of(Hash, compile.send(:instance_variable_get, "@#{table}"), "Did not set %s table correctly" % table) end assert_instance_of(Scope, compile.topscope, "Did not create a topscope") graph = compile.instance_variable_get("@scope_graph") - assert_instance_of(GRATR::Digraph, graph, "Did not create scope graph") + assert_instance_of(Puppet::SimpleGraph, graph, "Did not create scope graph") assert(graph.vertex?(compile.topscope), "Did not add top scope as a vertex in the graph") end # Make sure we store and can retrieve references to classes and their scopes. def test_class_set_and_class_scope klass = mock 'ast_class' klass.expects(:classname).returns("myname") compile = mkcompile compile.catalog.expects(:tag).with("myname") assert_nothing_raised("Could not set class") do compile.class_set "myname", "myscope" end # First try to retrieve it by name. assert_equal("myscope", compile.class_scope("myname"), "Could not retrieve class scope by name") # Then by object assert_equal("myscope", compile.class_scope(klass), "Could not retrieve class scope by object") end def test_classlist compile = mkcompile compile.class_set "", "empty" compile.class_set "one", "yep" compile.class_set "two", "nope" # Make sure our class list is correct assert_equal(%w{one two}.sort, compile.classlist.sort, "Did not get correct class list") end # Make sure collections get added to our internal array def test_add_collection compile = mkcompile assert_nothing_raised("Could not add collection") do compile.add_collection "nope" end assert_equal(%w{nope}, compile.instance_variable_get("@collections"), "Did not add collection") end # Make sure we create a graph of scopes. def test_newscope compile = mkcompile graph = compile.instance_variable_get("@scope_graph") assert_instance_of(Scope, compile.topscope, "Did not create top scope") - assert_instance_of(GRATR::Digraph, graph, "Did not create graph") + assert_instance_of(Puppet::SimpleGraph, graph, "Did not create graph") assert(graph.vertex?(compile.topscope), "The top scope is not a vertex in the graph") # Now that we've got the top scope, create a new, subscope subscope = nil assert_nothing_raised("Could not create subscope") do subscope = compile.newscope(compile.topscope) end assert_instance_of(Scope, subscope, "Did not create subscope") assert(graph.edge?(compile.topscope, subscope), "An edge between top scope and subscope was not added") # Make sure a scope can find its parent. assert(compile.parent(subscope), "Could not look up parent scope on compile") assert_equal(compile.topscope.object_id, compile.parent(subscope).object_id, "Did not get correct parent scope from compile") assert_equal(compile.topscope.object_id, subscope.parent.object_id, "Scope did not correctly retrieve its parent scope") # Now create another, this time specifying options another = nil assert_nothing_raised("Could not create subscope") do another = compile.newscope(subscope, :level => 5) end assert_equal(5, another.level, "did not set scope option correctly") assert_instance_of(Scope, another, "Did not create second subscope") assert(graph.edge?(subscope, another), "An edge between parent scope and second subscope was not added") # Make sure it can find its parent. assert(compile.parent(another), "Could not look up parent scope of second subscope on compile") assert_equal(subscope.object_id, compile.parent(another).object_id, "Did not get correct parent scope of second subscope from compile") assert_equal(subscope.object_id, another.parent.object_id, "Second subscope did not correctly retrieve its parent scope") # And make sure both scopes show up in the right order in the search path assert_equal([another.object_id, subscope.object_id, compile.topscope.object_id], another.scope_path.collect { |p| p.object_id }, "Did not get correct scope path") end # The heart of the action. def test_compile compile = mkcompile [:set_node_parameters, :evaluate_main, :evaluate_ast_node, :evaluate_node_classes, :evaluate_generators, :fail_on_unevaluated, :finish].each do |method| compile.expects(method) end assert_instance_of(Puppet::Node::Catalog, compile.compile, "Did not return the catalog") end # Test setting the node's parameters into the top scope. def test_set_node_parameters compile = mkcompile @node.parameters = {"a" => "b", "c" => "d"} scope = compile.topscope @node.parameters.each do |param, value| scope.expects(:setvar).with(param, value) end assert_nothing_raised("Could not call 'set_node_parameters'") do compile.send(:set_node_parameters) end end # Test that we can evaluate the main class, which is the one named "" in namespace # "". def test_evaluate_main compile = mkcompile main_class = mock 'main_class' compile.topscope.expects(:source=).with(main_class) @parser.expects(:findclass).with("", "").returns(main_class) main_resource = mock 'main resource' Puppet::Parser::Resource.expects(:new).with { |args| args[:title] == :main }.returns(main_resource) main_resource.expects(:evaluate) assert_nothing_raised("Could not call evaluate_main") do compile.send(:evaluate_main) end end def test_evaluate_node_classes compile = mkcompile @node.classes = %w{one two three four} compile.expects(:evaluate_classes).with(%w{one two three four}, compile.topscope) assert_nothing_raised("could not call evaluate_node_classes") do compile.send(:evaluate_node_classes) end end def test_evaluate_collections compile = mkcompile colls = [] # Make sure we return false when there's nothing there. assert(! compile.send(:evaluate_collections), "Returned true when there were no collections") # And when the collections fail to evaluate. colls << mock("coll1-false") colls << mock("coll2-false") colls.each { |c| c.expects(:evaluate).returns(false) } compile.instance_variable_set("@collections", colls) assert(! compile.send(:evaluate_collections), "Returned true when collections both evaluated nothing") # Now have one of the colls evaluate colls.clear colls << mock("coll1-one-true") colls << mock("coll2-one-true") colls[0].expects(:evaluate).returns(true) colls[1].expects(:evaluate).returns(false) assert(compile.send(:evaluate_collections), "Did not return true when one collection evaluated true") # And have them both eval true colls.clear colls << mock("coll1-both-true") colls << mock("coll2-both-true") colls[0].expects(:evaluate).returns(true) colls[1].expects(:evaluate).returns(true) assert(compile.send(:evaluate_collections), "Did not return true when both collections evaluated true") end def test_unevaluated_resources compile = mkcompile resources = {} compile.instance_variable_set("@resource_table", resources) # First test it when the table is empty assert_nil(compile.send(:unevaluated_resources), "Somehow found unevaluated resources in an empty table") # Then add a builtin resources resources["one"] = mock("builtin only") resources["one"].expects(:builtin?).returns(true) assert_nil(compile.send(:unevaluated_resources), "Considered a builtin resource unevaluated") # And do both builtin and non-builtin but already evaluated resources.clear resources["one"] = mock("builtin (with eval)") resources["one"].expects(:builtin?).returns(true) resources["two"] = mock("evaled (with builtin)") resources["two"].expects(:builtin?).returns(false) resources["two"].expects(:evaluated?).returns(true) assert_nil(compile.send(:unevaluated_resources), "Considered either a builtin or evaluated resource unevaluated") # Now a single unevaluated resource. resources.clear resources["one"] = mock("unevaluated") resources["one"].expects(:builtin?).returns(false) resources["one"].expects(:evaluated?).returns(false) assert_equal([resources["one"]], compile.send(:unevaluated_resources), "Did not find unevaluated resource") # With two uneval'ed resources, and an eval'ed one thrown in resources.clear resources["one"] = mock("unevaluated one") resources["one"].expects(:builtin?).returns(false) resources["one"].expects(:evaluated?).returns(false) resources["two"] = mock("unevaluated two") resources["two"].expects(:builtin?).returns(false) resources["two"].expects(:evaluated?).returns(false) resources["three"] = mock("evaluated") resources["three"].expects(:builtin?).returns(false) resources["three"].expects(:evaluated?).returns(true) result = compile.send(:unevaluated_resources) %w{one two}.each do |name| assert(result.include?(resources[name]), "Did not find %s in the unevaluated list" % name) end end def test_evaluate_definitions # First try the case where there's nothing to return compile = mkcompile compile.expects(:unevaluated_resources).returns(nil) assert_nothing_raised("Could not test for unevaluated resources") do assert(! compile.send(:evaluate_definitions), "evaluate_definitions returned true when no resources were evaluated") end # Now try it with resources left to evaluate resources = [] res1 = mock("resource1") res1.expects(:evaluate) res2 = mock("resource2") res2.expects(:evaluate) resources << res1 << res2 compile = mkcompile compile.expects(:unevaluated_resources).returns(resources) assert_nothing_raised("Could not test for unevaluated resources") do assert(compile.send(:evaluate_definitions), "evaluate_definitions returned false when resources were evaluated") end end def test_evaluate_generators # First try the case where we have nothing to do compile = mkcompile compile.expects(:evaluate_definitions).returns(false) compile.expects(:evaluate_collections).returns(false) assert_nothing_raised("Could not call :eval_iterate") do compile.send(:evaluate_generators) end # FIXME I could not get this test to work, but the code is short # enough that I'm ok with it. # It's important that collections are evaluated before definitions, # so make sure that's the case by verifying that collections get tested # twice but definitions only once. #compile = mkcompile #compile.expects(:evaluate_collections).returns(true).returns(false) #compile.expects(:evaluate_definitions).returns(false) #compile.send(:eval_iterate) end def test_store compile = mkcompile Puppet.features.expects(:rails?).returns(true) Puppet::Rails.expects(:connect) node = mock 'node' resource_table = mock 'resources' resource_table.expects(:values).returns(:resources) compile.instance_variable_set("@node", node) compile.instance_variable_set("@resource_table", resource_table) compile.expects(:store_to_active_record).with(node, :resources) compile.send(:store) end def test_store_to_active_record compile = mkcompile node = mock 'node' node.expects(:name).returns("myname") Puppet::Rails::Host.stubs(:transaction).yields Puppet::Rails::Host.expects(:store).with(node, :resources) compile.send(:store_to_active_record, node, :resources) end # Make sure that 'finish' gets called on all of our resources. def test_finish compile = mkcompile table = compile.instance_variable_get("@resource_table") # Add a resource that does respond to :finish yep = mock("finisher") yep.expects(:respond_to?).with(:finish).returns(true) yep.expects(:finish) table["yep"] = yep # And one that does not dnf = mock("dnf") dnf.expects(:respond_to?).with(:finish).returns(false) table["dnf"] = dnf compile.send(:finish) end def test_verify_uniqueness compile = mkcompile resources = compile.instance_variable_get("@resource_table") resource = mock("noconflict") resource.expects(:ref).returns("File[yay]") assert_nothing_raised("Raised an exception when there should have been no conflict") do compile.send(:verify_uniqueness, resource) end # Now try the case where our type is isomorphic resources["thing"] = true isoconflict = mock("isoconflict") isoconflict.expects(:ref).returns("thing") isoconflict.expects(:type).returns("testtype") faketype = mock("faketype") faketype.expects(:isomorphic?).returns(false) faketype.expects(:name).returns("whatever") Puppet::Type.expects(:type).with("testtype").returns(faketype) assert_nothing_raised("Raised an exception when was a conflict in non-isomorphic types") do compile.send(:verify_uniqueness, isoconflict) end # Now test for when we actually have an exception initial = mock("initial") resources["thing"] = initial initial.expects(:file).returns(false) conflict = mock("conflict") conflict.expects(:ref).returns("thing").times(2) conflict.expects(:type).returns("conflict") conflict.expects(:file).returns(false) conflict.expects(:line).returns(false) faketype = mock("faketype") faketype.expects(:isomorphic?).returns(true) Puppet::Type.expects(:type).with("conflict").returns(faketype) assert_raise(Puppet::ParseError, "Did not fail when two isomorphic resources conflicted") do compile.send(:verify_uniqueness, conflict) end end def test_store_resource # Run once when there's no conflict compile = mkcompile table = compile.instance_variable_get("@resource_table") resource = mock("resource") resource.expects(:ref).returns("yay") compile.expects(:verify_uniqueness).with(resource) scope = stub("scope", :resource => mock('resource')) compile.catalog.expects(:add_edge!).with(scope.resource, resource) assert_nothing_raised("Could not store resource") do compile.store_resource(scope, resource) end assert_equal(resource, table["yay"], "Did not store resource in table") # Now for conflicts compile = mkcompile table = compile.instance_variable_get("@resource_table") resource = mock("resource") compile.expects(:verify_uniqueness).with(resource).raises(ArgumentError) assert_raise(ArgumentError, "Did not raise uniqueness exception") do compile.store_resource(scope, resource) end assert(table.empty?, "Conflicting resource was stored in table") end def test_fail_on_unevaluated compile = mkcompile compile.expects(:fail_on_unevaluated_overrides) compile.expects(:fail_on_unevaluated_resource_collections) compile.send :fail_on_unevaluated end def test_store_override # First test the case when the resource is not present. compile = mkcompile overrides = compile.instance_variable_get("@resource_overrides") override = Object.new override.expects(:ref).returns(:myref).times(2) override.expects(:override=).with(true) assert_nothing_raised("Could not call store_override") do compile.store_override(override) end assert_instance_of(Array, overrides[:myref], "Overrides table is not a hash of arrays") assert_equal(override, overrides[:myref][0], "Did not store override in appropriately named array") # And when the resource already exists. resource = mock 'resource' resources = compile.instance_variable_get("@resource_table") resources[:resref] = resource override = mock 'override' resource.expects(:merge).with(override) override.expects(:override=).with(true) override.expects(:ref).returns(:resref) assert_nothing_raised("Could not call store_override when the resource already exists.") do compile.store_override(override) end end def test_resource_overrides compile = mkcompile overrides = compile.instance_variable_get("@resource_overrides") overrides[:test] = :yay resource = mock 'resource' resource.expects(:ref).returns(:test) assert_equal(:yay, compile.resource_overrides(resource), "Did not return overrides from table") end def test_fail_on_unevaluated_resource_collections compile = mkcompile collections = compile.instance_variable_get("@collections") # Make sure we're fine when the list is empty assert_nothing_raised("Failed when no collections were present") do compile.send :fail_on_unevaluated_resource_collections end # And that we're fine when we've got collections but with no resources collections << mock('coll') collections[0].expects(:resources).returns(nil) assert_nothing_raised("Failed when no resource collections were present") do compile.send :fail_on_unevaluated_resource_collections end # But that we do fail when we've got resource collections left. collections.clear # return both an array and a string, because that's tested internally collections << mock('coll returns one') collections[0].expects(:resources).returns(:something) collections << mock('coll returns many') collections[1].expects(:resources).returns([:one, :two]) assert_raise(Puppet::ParseError, "Did not fail on unevaluated resource collections") do compile.send :fail_on_unevaluated_resource_collections end end def test_fail_on_unevaluated_overrides compile = mkcompile overrides = compile.instance_variable_get("@resource_overrides") # Make sure we're fine when the list is empty assert_nothing_raised("Failed when no collections were present") do compile.send :fail_on_unevaluated_overrides end # But that we fail if there are any overrides left in the table. overrides[:yay] = [] overrides[:foo] = [] overrides[:bar] = [mock("override")] overrides[:bar][0].expects(:ref).returns("yay") assert_raise(Puppet::ParseError, "Failed to fail when overrides remain") do compile.send :fail_on_unevaluated_overrides end end def test_find_resource compile = mkcompile resources = compile.instance_variable_get("@resource_table") assert_nothing_raised("Could not call findresource when the resource table was empty") do assert_nil(compile.findresource("yay", "foo"), "Returned a non-existent resource") assert_nil(compile.findresource("yay[foo]"), "Returned a non-existent resource") end resources["Foo[bar]"] = :yay assert_nothing_raised("Could not call findresource when the resource table was not empty") do assert_equal(:yay, compile.findresource("foo", "bar"), "Returned a non-existent resource") assert_equal(:yay, compile.findresource("Foo[bar]"), "Returned a non-existent resource") end end # #620 - Nodes and classes should conflict, else classes don't get evaluated def test_nodes_and_classes_name_conflict # Test node then class compile = mkcompile node = stub :nodescope? => true klass = stub :nodescope? => false compile.class_set("one", node) assert_raise(Puppet::ParseError, "Did not fail when replacing node with class") do compile.class_set("one", klass) end # and class then node compile = mkcompile node = stub :nodescope? => true klass = stub :nodescope? => false compile.class_set("two", klass) assert_raise(Puppet::ParseError, "Did not fail when replacing node with class") do compile.class_set("two", node) end end end diff --git a/test/language/resource.rb b/test/language/resource.rb index 84a30b029..5a3916159 100755 --- a/test/language/resource.rb +++ b/test/language/resource.rb @@ -1,493 +1,493 @@ #!/usr/bin/env ruby require File.dirname(__FILE__) + '/../lib/puppettest' require 'puppettest' require 'puppettest/resourcetesting' class TestResource < PuppetTest::TestCase include PuppetTest include PuppetTest::ParserTesting include PuppetTest::ResourceTesting Parser = Puppet::Parser AST = Parser::AST Resource = Puppet::Parser::Resource Reference = Puppet::Parser::Resource::Reference def setup super Puppet[:trace] = false end def teardown mocha_verify end def test_initialize args = {:type => "resource", :title => "testing", :scope => mkscope} # Check our arg requirements args.each do |name, value| try = args.dup try.delete(name) assert_raise(ArgumentError, "Did not fail when %s was missing" % name) do Parser::Resource.new(try) end end res = nil assert_nothing_raised do res = Parser::Resource.new(args) end ref = res.instance_variable_get("@ref") assert_equal("Resource", ref.type, "did not set resource type") assert_equal("testing", ref.title, "did not set resource title") end def test_merge res = mkresource other = mkresource # First try the case where the resource is not allowed to override res.source = "source1" other.source = "source2" other.source.expects(:child_of?).with("source1").returns(false) assert_raise(Puppet::ParseError, "Allowed unrelated resources to override") do res.merge(other) end # Next try it when the sources are equal. res.source = "source3" other.source = res.source other.source.expects(:child_of?).with("source3").never params = {:a => :b, :c => :d} other.expects(:params).returns(params) res.expects(:override_parameter).with(:b) res.expects(:override_parameter).with(:d) res.merge(other) # And then parentage is involved other = mkresource res.source = "source3" other.source = "source4" other.source.expects(:child_of?).with("source3").returns(true) params = {:a => :b, :c => :d} other.expects(:params).returns(params) res.expects(:override_parameter).with(:b) res.expects(:override_parameter).with(:d) res.merge(other) end # the [] method def test_array_accessors res = mkresource params = res.instance_variable_get("@params") assert_nil(res[:missing], "Found a missing parameter somehow") params[:something] = stub(:value => "yay") assert_equal("yay", res[:something], "Did not correctly call value on the parameter") res.expects(:title).returns(:mytitle) assert_equal(:mytitle, res[:title], "Did not call title when asked for it as a param") end # Make sure any defaults stored in the scope get added to our resource. def test_add_defaults res = mkresource params = res.instance_variable_get("@params") params[:a] = :b res.scope.expects(:lookupdefaults).with(res.type).returns(:a => :replaced, :c => :d) res.expects(:debug) res.send(:add_defaults) assert_equal(:d, params[:c], "Did not set default") assert_equal(:b, params[:a], "Replaced parameter with default") end def test_finish res = mkresource res.expects(:add_overrides) res.expects(:add_defaults) res.expects(:add_metaparams) res.expects(:validate) res.finish end # Make sure we paramcheck our params def test_validate res = mkresource params = res.instance_variable_get("@params") params[:one] = :two params[:three] = :four res.expects(:paramcheck).with(:one) res.expects(:paramcheck).with(:three) res.send(:validate) end def test_override_parameter res = mkresource params = res.instance_variable_get("@params") # There are three cases, with the second having two options: # No existing parameter. param = stub(:name => "myparam") res.send(:override_parameter, param) assert_equal(param, params["myparam"], "Override was not added to param list") # An existing parameter that we can override. source = stub(:child_of? => true) # Start out without addition params["param2"] = stub(:source => :whatever) param = stub(:name => "param2", :source => source, :add => false) res.send(:override_parameter, param) assert_equal(param, params["param2"], "Override was not added to param list") # Try with addition. params["param2"] = stub(:value => :a, :source => :whatever) param = stub(:name => "param2", :source => source, :add => true, :value => :b) param.expects(:value=).with([:a, :b]) res.send(:override_parameter, param) assert_equal(param, params["param2"], "Override was not added to param list") # And finally, make sure we throw an exception when the sources aren't related source = stub(:child_of? => false) params["param2"] = stub(:source => :whatever, :file => :f, :line => :l) old = params["param2"] param = stub(:name => "param2", :source => source, :file => :f, :line => :l) assert_raise(Puppet::ParseError, "Did not fail when params conflicted") do res.send(:override_parameter, param) end assert_equal(old, params["param2"], "Param was replaced irrespective of conflict") end def test_set_parameter res = mkresource params = res.instance_variable_get("@params") # First test the simple case: It's already a parameter param = mock('param') param.expects(:is_a?).with(Resource::Param).returns(true) param.expects(:name).returns("pname") res.send(:set_parameter, param) assert_equal(param, params["pname"], "Parameter was not added to hash") # Now the case where there's no value but it's not a param param = mock('param') param.expects(:is_a?).with(Resource::Param).returns(false) assert_raise(ArgumentError, "Did not fail when a non-param was passed") do res.send(:set_parameter, param) end # and the case where a value is passed in param = stub :name => "pname", :value => "whatever" Resource::Param.expects(:new).with(:name => "pname", :value => "myvalue", :source => res.source).returns(param) res.send(:set_parameter, "pname", "myvalue") assert_equal(param, params["pname"], "Did not put param in hash") end def test_paramcheck # There are three cases here: # It's a valid parameter res = mkresource ref = mock('ref') res.instance_variable_set("@ref", ref) klass = mock("class") ref.expects(:typeclass).returns(klass).times(4) klass.expects(:validattr?).with("good").returns(true) assert(res.send(:paramcheck, :good), "Did not allow valid param") # It's name or title klass.expects(:validattr?).with("name").returns(false) assert(res.send(:paramcheck, :name), "Did not allow name") klass.expects(:validattr?).with("title").returns(false) assert(res.send(:paramcheck, :title), "Did not allow title") # It's not actually allowed klass.expects(:validattr?).with("other").returns(false) res.expects(:fail) ref.expects(:type) res.send(:paramcheck, :other) end def test_to_transobject # First try translating a builtin resource. Make sure we use some references # and arrays, to make sure they translate correctly. source = mock("source") scope = mkscope scope.stubs(:tags).returns([]) refs = [] 4.times { |i| refs << Puppet::Parser::Resource::Reference.new(:title => "file%s" % i, :type => "file") } res = Parser::Resource.new :type => "file", :title => "/tmp", :source => source, :scope => scope, :params => paramify(source, :owner => "nobody", :group => %w{you me}, :require => refs[0], :ignore => %w{svn}, :subscribe => [refs[1], refs[2]], :notify => [refs[3]]) obj = nil assert_nothing_raised do obj = res.to_trans end assert_instance_of(Puppet::TransObject, obj) assert_equal(obj.type, res.type.downcase) assert_equal(obj.name, res.title) # TransObjects use strings, resources use symbols assert_equal("nobody", obj["owner"], "Single-value string was not passed correctly") assert_equal(%w{you me}, obj["group"], "Array of strings was not passed correctly") assert_equal("svn", obj["ignore"], "Array with single string was not turned into single value") assert_equal(["file", refs[0].title], obj["require"], "Resource reference was not passed correctly") assert_equal([["file", refs[1].title], ["file", refs[2].title]], obj["subscribe"], "Array of resource references was not passed correctly") assert_equal(["file", refs[3].title], obj["notify"], "Array with single resource reference was not turned into single value") end # FIXME This isn't a great test, but I need to move on. def test_to_transbucket bucket = mock("transbucket") source = mock("source") scope = mkscope res = Parser::Resource.new :type => "mydefine", :title => "yay", :source => source, :scope => scope result = res.to_trans assert_equal("yay", result.name, "did not set bucket name correctly") assert_equal("Mydefine", result.type, "did not set bucket type correctly") end def test_evaluate # First try the most common case, we're not a builtin type. res = mkresource ref = res.instance_variable_get("@ref") type = mock("type") ref.expects(:definedtype).returns(type) res.expects(:finish) res.scope = mock("scope") config = mock("config") res.scope.expects(:compile).returns(config) config.expects(:delete_resource).with(res) args = {:scope => res.scope, :resource => res} type.expects(:evaluate).with(args) res.evaluate end def test_add_overrides # Try it with nil res = mkresource res.scope = mock('scope') config = mock("config") res.scope.expects(:compile).returns(config) config.expects(:resource_overrides).with(res).returns(nil) res.expects(:merge).never res.send(:add_overrides) # And an empty array res = mkresource res.scope = mock('scope') config = mock("config") res.scope.expects(:compile).returns(config) config.expects(:resource_overrides).with(res).returns([]) res.expects(:merge).never res.send(:add_overrides) # And with some overrides res = mkresource res.scope = mock('scope') config = mock("config") res.scope.expects(:compile).returns(config) returns = %w{a b} config.expects(:resource_overrides).with(res).returns(returns) res.expects(:merge).with("a") res.expects(:merge).with("b") res.send(:add_overrides) assert(returns.empty?, "Did not clear overrides") end def test_proxymethods res = Parser::Resource.new :type => "evaltest", :title => "yay", :source => mock("source"), :scope => mkscope assert_equal("Evaltest", res.type) assert_equal("yay", res.title) assert_equal(false, res.builtin?) end def test_reference_conversion # First try it as a normal string ref = Parser::Resource::Reference.new(:type => "file", :title => "/tmp/ref1") # Now create an obj that uses it res = mkresource :type => "file", :title => "/tmp/resource", :params => {:require => ref} res.scope = mkscope trans = nil assert_nothing_raised do trans = res.to_trans end assert_instance_of(Array, trans["require"]) assert_equal(["file", "/tmp/ref1"], trans["require"]) # Now try it when using an array of references. two = Parser::Resource::Reference.new(:type => "file", :title => "/tmp/ref2") res = mkresource :type => "file", :title => "/tmp/resource2", :params => {:require => [ref, two]} res.scope = mkscope trans = nil assert_nothing_raised do trans = res.to_trans end assert_instance_of(Array, trans["require"][0]) trans["require"].each do |val| assert_instance_of(Array, val) assert_equal("file", val[0]) assert(val[1] =~ /\/tmp\/ref[0-9]/, "Was %s instead of the file name" % val[1]) end end # This is a bit of a weird one -- the user should not actually know # that components exist, so we want references to act like they're not # builtin def test_components_are_not_builtin ref = Parser::Resource::Reference.new(:type => "component", :title => "yay") assert_nil(ref.builtintype, "Definition was considered builtin") end # The second part of #539 - make sure resources pass the arguments # correctly. def test_title_with_definitions parser = mkparser define = parser.newdefine "yayness", :code => resourcedef("file", "/tmp", "owner" => varref("name"), "mode" => varref("title")) klass = parser.findclass("", "") should = {:name => :owner, :title => :mode} [ {:name => "one", :title => "two"}, {:title => "three"}, ].each do |hash| config = mkcompile parser args = {:type => "yayness", :title => hash[:title], :source => klass, :scope => config.topscope} if hash[:name] args[:params] = {:name => hash[:name]} else args[:params] = {} # override the defaults end res = nil assert_nothing_raised("Could not create res with %s" % hash.inspect) do res = mkresource(args) end assert_nothing_raised("Could not eval res with %s" % hash.inspect) do res.evaluate end made = config.topscope.findresource("File[/tmp]") assert(made, "Did not create resource with %s" % hash.inspect) should.each do |orig, param| assert_equal(hash[orig] || hash[:title], made[param], "%s was not set correctly with %s" % [param, hash.inspect]) end end end # part of #629 -- the undef keyword. Make sure 'undef' params get skipped. def test_undef_and_to_hash res = mkresource :type => "file", :title => "/tmp/testing", :source => mock("source"), :scope => mkscope, :params => {:owner => :undef, :mode => "755"} hash = nil assert_nothing_raised("Could not convert resource with undef to hash") do hash = res.to_hash end assert_nil(hash[:owner], "got a value for an undef parameter") end # #643 - Make sure virtual defines result in virtual resources def test_virtual_defines parser = mkparser define = parser.newdefine("yayness", :code => resourcedef("file", varref("name"), "mode" => "644")) config = mkcompile(parser) res = mkresource :type => "yayness", :title => "foo", :params => {}, :scope => config.topscope res.virtual = true result = nil assert_nothing_raised("Could not evaluate defined resource") do result = res.evaluate end scope = res.scope newres = scope.findresource("File[foo]") assert(newres, "Could not find resource") assert(newres.virtual?, "Virtual defined resource generated non-virtual resources") # Now try it with exported resources res = mkresource :type => "yayness", :title => "bar", :params => {}, :scope => config.topscope res.exported = true result = nil assert_nothing_raised("Could not evaluate exported resource") do result = res.evaluate end scope = res.scope newres = scope.findresource("File[bar]") assert(newres, "Could not find resource") assert(newres.exported?, "Exported defined resource generated non-exported resources") assert(newres.virtual?, "Exported defined resource generated non-virtual resources") end # Make sure tags behave appropriately. def test_tags scope_resource = stub 'scope_resource', :tags => %w{srone srtwo} scope = stub 'scope', :resource => scope_resource resource = Puppet::Parser::Resource.new(:type => "file", :title => "yay", :scope => scope, :source => mock('source')) - # Make sure we get the scope resource's tags, plus the type and title - %w{srone srtwo yay file}.each do |tag| + # Make sure we get the type and title + %w{yay file}.each do |tag| assert(resource.tags.include?(tag), "Did not tag resource with %s" % tag) end # make sure we can only set legal tags ["an invalid tag", "-anotherinvalid", "bad*tag"].each do |tag| assert_raise(Puppet::ParseError, "Tag #{tag} was considered valid") do resource.tag tag end end # make sure good tags make it through. tags = %w{good-tag yaytag GoodTag another_tag a ab A} tags.each do |tag| assert_nothing_raised("Tag #{tag} was considered invalid") do resource.tag tag end end # make sure we get each of them. ptags = resource.tags tags.each do |tag| assert(ptags.include?(tag.downcase), "missing #{tag}") end end end