rspec-puppet 0.0.1 → 0.0.2
Sign up to get free protection for your applications and to get access to all the features.
- data/LICENSE +20 -0
- data/README.md +126 -0
- data/Rakefile +6 -0
- data/lib/rspec-puppet.rb +4 -0
- data/lib/rspec-puppet/example.rb +2 -2
- data/lib/rspec-puppet/example/class_example_group.rb +13 -3
- data/lib/rspec-puppet/example/define_example_group.rb +11 -2
- data/rspec-puppet.gemspec +14 -7
- data/spec/classes/sysctl_common_spec.rb +7 -0
- data/spec/defines/sysctl_spec.rb +13 -0
- data/spec/fixtures/sysctl/manifests/init.pp +18 -0
- data/spec/spec_helper.rb +5 -0
- metadata +16 -9
data/LICENSE
ADDED
@@ -0,0 +1,20 @@
|
|
1
|
+
Copyright (c) 2011 Tim Sharpe
|
2
|
+
|
3
|
+
Permission is hereby granted, free of charge, to any person obtaining
|
4
|
+
a copy of this software and associated documentation files (the
|
5
|
+
"Software"), to deal in the Software without restriction, including
|
6
|
+
without limitation the rights to use, copy, modify, merge, publish,
|
7
|
+
distribute, sublicense, and/or sell copies of the Software, and to
|
8
|
+
permit persons to whom the Software is furnished to do so, subject to
|
9
|
+
the following conditions:
|
10
|
+
|
11
|
+
The above copyright notice and this permission notice shall be
|
12
|
+
included in all copies or substantial portions of the Software.
|
13
|
+
|
14
|
+
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
|
15
|
+
EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
|
16
|
+
MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
|
17
|
+
IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
|
18
|
+
CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
|
19
|
+
TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
|
20
|
+
SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
|
data/README.md
ADDED
@@ -0,0 +1,126 @@
|
|
1
|
+
# RSpec tests for your Puppet manifests
|
2
|
+
|
3
|
+
## Installation
|
4
|
+
|
5
|
+
gem install rspec-puppet
|
6
|
+
|
7
|
+
## Naming conventions
|
8
|
+
|
9
|
+
For clarity and consistency, I recommend that you use the following directory
|
10
|
+
structure and naming convention.
|
11
|
+
|
12
|
+
module
|
13
|
+
|
|
14
|
+
+-- manifests
|
15
|
+
|
|
16
|
+
+-- lib
|
17
|
+
|
|
18
|
+
+-- spec
|
19
|
+
|
|
20
|
+
+-- spec_helper.rb
|
21
|
+
|
|
22
|
+
+-- classes
|
23
|
+
| |
|
24
|
+
| +-- <class_name>_spec.rb
|
25
|
+
|
|
26
|
+
+-- defines
|
27
|
+
|
|
28
|
+
+-- <define_name>_spec.rb
|
29
|
+
|
30
|
+
## Example groups
|
31
|
+
|
32
|
+
If you use the above directory structure, your examples will automatically be
|
33
|
+
placed in the correct groups and have access to the custom matchers. If you
|
34
|
+
choose not to, you can force the examples into the required groups as follows.
|
35
|
+
|
36
|
+
describe 'myclass', :type => :class do
|
37
|
+
...
|
38
|
+
end
|
39
|
+
|
40
|
+
describe 'mydefine', :type => :define do
|
41
|
+
...
|
42
|
+
end
|
43
|
+
|
44
|
+
## Matchers
|
45
|
+
|
46
|
+
### Checking if a class has been included
|
47
|
+
|
48
|
+
You can test if a class has been included in the catalogue with the
|
49
|
+
`include_class` matcher. It takes the class name as a string as its only
|
50
|
+
argument
|
51
|
+
|
52
|
+
it { should include_class('foo') }
|
53
|
+
|
54
|
+
### Checking if a resources exists
|
55
|
+
|
56
|
+
You can test if a resource exists in the catalogue with the generic
|
57
|
+
`creates_<resource type>` matcher. If your resource type includes :: (e.g.
|
58
|
+
`foo::bar` simply replace the :: with -
|
59
|
+
|
60
|
+
it { should create_augeas('bleh') }
|
61
|
+
it { should create_foo-bar('baz') }
|
62
|
+
|
63
|
+
You can further test the parameters that have been passed to the resources with
|
64
|
+
the generic `with_<parameter>` chains.
|
65
|
+
|
66
|
+
it { should create_package('mysql-server').with_ensure('present') }
|
67
|
+
|
68
|
+
## Writing tests
|
69
|
+
|
70
|
+
### Basic test structure
|
71
|
+
|
72
|
+
To test that
|
73
|
+
|
74
|
+
sysctl { 'baz'
|
75
|
+
value => 'foo',
|
76
|
+
}
|
77
|
+
|
78
|
+
Will cause the following resource to be in included in catalogue for a host
|
79
|
+
|
80
|
+
exec { 'sysctl/reload':
|
81
|
+
command => '/sbin/sysctl -p /etc/sysctl.conf',
|
82
|
+
}
|
83
|
+
|
84
|
+
We can write the following testcase
|
85
|
+
|
86
|
+
describe 'sysctl' do
|
87
|
+
let(:title) { 'baz' }
|
88
|
+
let(:params) { { :value => 'foo' } }
|
89
|
+
|
90
|
+
it { should create_exec('sysctl/reload').with_command("/sbin/sysctl -p /etc/sysctl.conf") }
|
91
|
+
end
|
92
|
+
|
93
|
+
### Specifying the title of a resource
|
94
|
+
|
95
|
+
let(:title) { 'foo' }
|
96
|
+
|
97
|
+
### Specifying the parameters to pass to a resources or parametised class
|
98
|
+
|
99
|
+
let(:params) { {:ensure => 'present', ...} }
|
100
|
+
|
101
|
+
### Specifying the FQDN of the test node
|
102
|
+
|
103
|
+
If the manifest you're testing expects to run on host with a particular name,
|
104
|
+
you can specify this as follows
|
105
|
+
|
106
|
+
let(:node) { 'testhost.example.com' }
|
107
|
+
|
108
|
+
### Specifying the facts that should be available to your manifest
|
109
|
+
|
110
|
+
By default, the test environment contains no facts for your manifest to use.
|
111
|
+
You can set them with a hash
|
112
|
+
|
113
|
+
let(:facts) { {:operatingsystem => 'Debian', :kernel => 'Linux', ...} }
|
114
|
+
|
115
|
+
### Specifying the path to find your modules
|
116
|
+
|
117
|
+
I recommend setting a default module path by adding the following code to your
|
118
|
+
`spec_helper.rb`
|
119
|
+
|
120
|
+
RSpec.configure do |c|
|
121
|
+
c.module_path = '/path/to/your/module/dir'
|
122
|
+
end
|
123
|
+
|
124
|
+
However, if you want to specify it in each example, you can do so
|
125
|
+
|
126
|
+
let(:module_path) { '/path/to/your/module/dir' }
|
data/Rakefile
ADDED
data/lib/rspec-puppet.rb
CHANGED
data/lib/rspec-puppet/example.rb
CHANGED
@@ -7,10 +7,10 @@ RSpec::configure do |c|
|
|
7
7
|
end
|
8
8
|
|
9
9
|
c.include RSpec::Puppet::DefineExampleGroup, :type => :define, :example_group => {
|
10
|
-
:file_path => c.escaped_path(%w[spec
|
10
|
+
:file_path => c.escaped_path(%w[spec defines])
|
11
11
|
}
|
12
12
|
|
13
13
|
c.include RSpec::Puppet::ClassExampleGroup, :type => :class, :example_group => {
|
14
|
-
:file_path => c.escaped_path(%w[spec
|
14
|
+
:file_path => c.escaped_path(%w[spec classes])
|
15
15
|
}
|
16
16
|
end
|
@@ -7,13 +7,23 @@ module RSpec::Puppet
|
|
7
7
|
end
|
8
8
|
|
9
9
|
def catalogue
|
10
|
-
Puppet[:modulepath] = module_path
|
10
|
+
Puppet[:modulepath] = self.respond_to?(:module_path) ? module_path : RSpec.configuration.module_path
|
11
11
|
|
12
12
|
klass_name = self.class.top_level_description.downcase
|
13
|
+
|
14
|
+
# If we're testing a standalone module (i.e. one that's outside of a
|
15
|
+
# puppet tree), the autoloader won't work, so we need to fudge it a bit.
|
16
|
+
if File.exists?(File.join(Puppet[:modulepath], 'manifests', 'init.pp'))
|
17
|
+
path_to_manifest = File.join([Puppet[:modulepath], 'manifests', klass_name.split('::')[1..-1]].flatten)
|
18
|
+
import_str = "import '#{Puppet[:modulepath]}/manifests/init.pp'\nimport '#{path_to_manifest}.pp'\n"
|
19
|
+
else
|
20
|
+
import_str = ""
|
21
|
+
end
|
22
|
+
|
13
23
|
if !self.respond_to?(:params) || params == {}
|
14
|
-
Puppet[:code] = "include #{klass_name}"
|
24
|
+
Puppet[:code] = import_str + "include #{klass_name}"
|
15
25
|
else
|
16
|
-
Puppet[:code] = 'class' + " { " + klass_name + ": " + params.keys.map { |r| "#{r.to_s} => '#{params[r].to_s}'"
|
26
|
+
Puppet[:code] = import_str + 'class' + " { " + klass_name + ": " + params.keys.map { |r| "#{r.to_s} => '#{params[r].to_s}'"
|
17
27
|
}.join(', ') + " }"
|
18
28
|
end
|
19
29
|
|
@@ -9,7 +9,16 @@ module RSpec::Puppet
|
|
9
9
|
def catalogue
|
10
10
|
define_name = self.class.top_level_description.downcase
|
11
11
|
|
12
|
-
Puppet[:modulepath] = module_path
|
12
|
+
Puppet[:modulepath] = self.respond_to?(:module_path) ? module_path : RSpec.configuration.module_path
|
13
|
+
|
14
|
+
# If we're testing a standalone module (i.e. one that's outside of a
|
15
|
+
# puppet tree), the autoloader won't work, so we need to fudge it a bit.
|
16
|
+
if File.exists?(File.join(Puppet[:modulepath], 'manifests', 'init.pp'))
|
17
|
+
path_to_manifest = File.join([Puppet[:modulepath], 'manifests', define_name.split('::')[1..-1]].flatten)
|
18
|
+
import_str = "import '#{Puppet[:modulepath]}/manifests/init.pp'\nimport '#{path_to_manifest}.pp'\n"
|
19
|
+
else
|
20
|
+
import_str = ""
|
21
|
+
end
|
13
22
|
|
14
23
|
if self.respond_to? :params
|
15
24
|
param_str = params.keys.map { |r|
|
@@ -19,7 +28,7 @@ module RSpec::Puppet
|
|
19
28
|
param_str = ""
|
20
29
|
end
|
21
30
|
|
22
|
-
Puppet[:code] = define_name + " { \"" + title + "\": " + param_str + " }"
|
31
|
+
Puppet[:code] = import_str + define_name + " { \"" + title + "\": " + param_str + " }"
|
23
32
|
|
24
33
|
nodename = self.respond_to?(:node) ? node : Puppet[:certname]
|
25
34
|
facts_val = self.respond_to?(:facts) ? facts : {}
|
data/rspec-puppet.gemspec
CHANGED
@@ -1,20 +1,27 @@
|
|
1
1
|
Gem::Specification.new do |s|
|
2
2
|
s.name = 'rspec-puppet'
|
3
|
-
s.version = '0.0.
|
3
|
+
s.version = '0.0.2'
|
4
4
|
s.homepage = 'https://github.com/rodjek/rspec-puppet/'
|
5
5
|
s.summary = 'RSpec tests for your Puppet manifests'
|
6
6
|
s.description = 'RSpec tests for your Puppet manifests'
|
7
7
|
|
8
8
|
s.files = [
|
9
|
-
'rspec-puppet.
|
10
|
-
'lib/rspec-puppet.rb',
|
11
|
-
'lib/rspec-puppet/
|
9
|
+
'lib/rspec-puppet/example/class_example_group.rb',
|
10
|
+
'lib/rspec-puppet/example/define_example_group.rb',
|
11
|
+
'lib/rspec-puppet/example.rb',
|
12
12
|
'lib/rspec-puppet/matchers/create_generic.rb',
|
13
13
|
'lib/rspec-puppet/matchers/create_resource.rb',
|
14
14
|
'lib/rspec-puppet/matchers/include_class.rb',
|
15
|
-
'lib/rspec-puppet/
|
16
|
-
'lib/rspec-puppet
|
17
|
-
'
|
15
|
+
'lib/rspec-puppet/matchers.rb',
|
16
|
+
'lib/rspec-puppet.rb',
|
17
|
+
'LICENSE',
|
18
|
+
'Rakefile',
|
19
|
+
'README.md',
|
20
|
+
'rspec-puppet.gemspec',
|
21
|
+
'spec/classes/sysctl_common_spec.rb',
|
22
|
+
'spec/defines/sysctl_spec.rb',
|
23
|
+
'spec/fixtures/sysctl/manifests/init.pp',
|
24
|
+
'spec/spec_helper.rb',
|
18
25
|
]
|
19
26
|
|
20
27
|
s.add_dependency 'rspec'
|
@@ -0,0 +1,13 @@
|
|
1
|
+
require 'spec_helper'
|
2
|
+
|
3
|
+
describe 'sysctl' do
|
4
|
+
let(:title) { 'vm.swappiness' }
|
5
|
+
let(:params) { {:value => '60'} }
|
6
|
+
|
7
|
+
it { should include_class('sysctl::common') }
|
8
|
+
it { should create_augeas('sysctl/vm.swappiness') \
|
9
|
+
.with_context('/files/etc/sysctl.conf') \
|
10
|
+
.with_changes("set vm.swappiness '60'") \
|
11
|
+
.with_onlyif("match vm.swappiness[.='60'] size == 0") \
|
12
|
+
.with_notify('Exec[sysctl/reload]') }
|
13
|
+
end
|
@@ -0,0 +1,18 @@
|
|
1
|
+
class sysctl::common {
|
2
|
+
exec { 'sysctl/reload':
|
3
|
+
command => '/sbin/sysctl -p /etc/sysctl.conf',
|
4
|
+
refreshonly => true,
|
5
|
+
returns => [0, 2],
|
6
|
+
}
|
7
|
+
}
|
8
|
+
|
9
|
+
define sysctl($value) {
|
10
|
+
include sysctl::common
|
11
|
+
|
12
|
+
augeas { "sysctl/${name}":
|
13
|
+
context => '/files/etc/sysctl.conf',
|
14
|
+
changes => "set ${name} '${value}'",
|
15
|
+
onlyif => "match ${name}[.='${value}'] size == 0",
|
16
|
+
notify => Exec['sysctl/reload'],
|
17
|
+
}
|
18
|
+
}
|
data/spec/spec_helper.rb
ADDED
metadata
CHANGED
@@ -1,13 +1,13 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: rspec-puppet
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
hash:
|
4
|
+
hash: 27
|
5
5
|
prerelease:
|
6
6
|
segments:
|
7
7
|
- 0
|
8
8
|
- 0
|
9
|
-
-
|
10
|
-
version: 0.0.
|
9
|
+
- 2
|
10
|
+
version: 0.0.2
|
11
11
|
platform: ruby
|
12
12
|
authors:
|
13
13
|
- Tim Sharpe
|
@@ -41,15 +41,22 @@ extensions: []
|
|
41
41
|
extra_rdoc_files: []
|
42
42
|
|
43
43
|
files:
|
44
|
-
- rspec-puppet.
|
45
|
-
- lib/rspec-puppet.rb
|
46
|
-
- lib/rspec-puppet/
|
44
|
+
- lib/rspec-puppet/example/class_example_group.rb
|
45
|
+
- lib/rspec-puppet/example/define_example_group.rb
|
46
|
+
- lib/rspec-puppet/example.rb
|
47
47
|
- lib/rspec-puppet/matchers/create_generic.rb
|
48
48
|
- lib/rspec-puppet/matchers/create_resource.rb
|
49
49
|
- lib/rspec-puppet/matchers/include_class.rb
|
50
|
-
- lib/rspec-puppet/
|
51
|
-
- lib/rspec-puppet
|
52
|
-
-
|
50
|
+
- lib/rspec-puppet/matchers.rb
|
51
|
+
- lib/rspec-puppet.rb
|
52
|
+
- LICENSE
|
53
|
+
- Rakefile
|
54
|
+
- README.md
|
55
|
+
- rspec-puppet.gemspec
|
56
|
+
- spec/classes/sysctl_common_spec.rb
|
57
|
+
- spec/defines/sysctl_spec.rb
|
58
|
+
- spec/fixtures/sysctl/manifests/init.pp
|
59
|
+
- spec/spec_helper.rb
|
53
60
|
has_rdoc: true
|
54
61
|
homepage: https://github.com/rodjek/rspec-puppet/
|
55
62
|
licenses: []
|