1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
|
require 'puppet'
require 'spec_helper'
describe 'function for dynamically creating resources' do
def get_scope
@topscope = Puppet::Parser::Scope.new
# This is necessary so we don't try to use the compiler to discover our parent.
@topscope.parent = nil
@scope = Puppet::Parser::Scope.new
@scope.compiler = Puppet::Parser::Compiler.new(Puppet::Node.new("floppy", :environment => 'production'))
@scope.parent = @topscope
@compiler = @scope.compiler
end
before :each do
get_scope
Puppet::Parser::Functions.function(:create_resources)
end
it "should exist" do
Puppet::Parser::Functions.function(:create_resources).should == "function_create_resources"
end
it 'should require two arguments' do
lambda { @scope.function_create_resources(['foo']) }.should raise_error(ArgumentError, 'create_resources(): wrong number of arguments (1; must be 2)')
end
describe 'when creating native types' do
before :each do
Puppet[:code]='notify{test:}'
get_scope
@scope.resource=Puppet::Parser::Resource.new('class', 't', :scope => @scope)
end
it 'empty hash should not cause resources to be added' do
@scope.function_create_resources(['file', {}])
@compiler.catalog.resources.size == 1
end
it 'should be able to add' do
@scope.function_create_resources(['file', {'/etc/foo'=>{'ensure'=>'present'}}])
@compiler.catalog.resource(:file, "/etc/foo")['ensure'].should == 'present'
end
it 'should accept multiple types' do
type_hash = {}
type_hash['foo'] = {'message' => 'one'}
type_hash['bar'] = {'message' => 'two'}
@scope.function_create_resources(['notify', type_hash])
@compiler.catalog.resource(:notify, "foo")['message'].should == 'one'
@compiler.catalog.resource(:notify, "bar")['message'].should == 'two'
end
it 'should fail to add non-existing type' do
lambda { @scope.function_create_resources(['foo', {}]) }.should raise_error(ArgumentError, 'could not create resource of unknown type foo')
end
it 'should be able to add edges' do
@scope.function_create_resources(['notify', {'foo'=>{'require' => 'Notify[test]'}}])
@scope.compiler.compile
rg = @scope.compiler.catalog.to_ral.relationship_graph
test = rg.vertices.find { |v| v.title == 'test' }
foo = rg.vertices.find { |v| v.title == 'foo' }
test.should be
foo.should be
rg.path_between(test,foo).should be
end
end
describe 'when dynamically creating resource types' do
before :each do
Puppet[:code]=
'define foo($one){notify{$name: message => $one}}
notify{test:}
'
get_scope
@scope.resource=Puppet::Parser::Resource.new('class', 't', :scope => @scope)
Puppet::Parser::Functions.function(:create_resources)
end
it 'should be able to create defined resoure types' do
@scope.function_create_resources(['foo', {'blah'=>{'one'=>'two'}}])
# still have to compile for this to work...
# I am not sure if this constraint ruins the tests
@scope.compiler.compile
@compiler.catalog.resource(:notify, "blah")['message'].should == 'two'
end
it 'should fail if defines are missing params' do
@scope.function_create_resources(['foo', {'blah'=>{}}])
lambda { @scope.compiler.compile }.should raise_error(Puppet::ParseError, /Must pass one to Foo\[blah\]/)
end
it 'should be able to add multiple defines' do
hash = {}
hash['blah'] = {'one' => 'two'}
hash['blaz'] = {'one' => 'three'}
@scope.function_create_resources(['foo', hash])
# still have to compile for this to work...
# I am not sure if this constraint ruins the tests
@scope.compiler.compile
@compiler.catalog.resource(:notify, "blah")['message'].should == 'two'
@compiler.catalog.resource(:notify, "blaz")['message'].should == 'three'
end
it 'should be able to add edges' do
@scope.function_create_resources(['foo', {'blah'=>{'one'=>'two', 'require' => 'Notify[test]'}}])
@scope.compiler.compile
rg = @scope.compiler.catalog.to_ral.relationship_graph
test = rg.vertices.find { |v| v.title == 'test' }
blah = rg.vertices.find { |v| v.title == 'blah' }
test.should be
blah.should be
# (Yoda speak like we do)
rg.path_between(test,blah).should be
@compiler.catalog.resource(:notify, "blah")['message'].should == 'two'
end
end
describe 'when creating classes' do
before :each do
Puppet[:code]=
'class bar($one){notify{test: message => $one}}
notify{tester:}
'
get_scope
@scope.resource=Puppet::Parser::Resource.new('class', 't', :scope => @scope)
Puppet::Parser::Functions.function(:create_resources)
end
it 'should be able to create classes', :'fails_on_ruby_1.9.2' => true do
@scope.function_create_resources(['class', {'bar'=>{'one'=>'two'}}])
@scope.compiler.compile
@compiler.catalog.resource(:notify, "test")['message'].should == 'two'
@compiler.catalog.resource(:class, "bar").should_not be_nil#['message'].should == 'two'
end
it 'should fail to create non-existing classes' do
lambda { @scope.function_create_resources(['class', {'blah'=>{'one'=>'two'}}]) }.should raise_error(ArgumentError ,'could not find hostclass blah')
end
it 'should be able to add edges', :'fails_on_ruby_1.9.2' => true do
@scope.function_create_resources(['class', {'bar'=>{'one'=>'two', 'require' => 'Notify[tester]'}}])
@scope.compiler.compile
rg = @scope.compiler.catalog.to_ral.relationship_graph
test = rg.vertices.find { |v| v.title == 'test' }
tester = rg.vertices.find { |v| v.title == 'tester' }
test.should be
tester.should be
rg.path_between(tester,test).should be
end
end
end
|