chefspec 3.3.0 → 3.3.1
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- checksums.yaml +4 -4
- data/CHANGELOG.md +11 -0
- data/README.md +3 -7
- data/chefspec.gemspec +0 -1
- data/lib/chefspec.rb +0 -4
- data/lib/chefspec/berkshelf.rb +8 -4
- data/lib/chefspec/coverage.rb +17 -72
- data/lib/chefspec/coverage/filters.rb +12 -2
- data/lib/chefspec/errors.rb +8 -6
- data/lib/chefspec/version.rb +1 -1
- data/spec/unit/errors_spec.rb +57 -0
- data/templates/coverage/human.erb +22 -0
- data/templates/errors/cookbook_path_not_found.erb +3 -0
- data/templates/errors/gem_load_error.erb +7 -0
- data/templates/errors/not_stubbed.erb +7 -0
- metadata +8 -23
- data/locales/en.yml +0 -19
checksums.yaml
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
---
|
2
2
|
SHA1:
|
3
|
-
metadata.gz:
|
4
|
-
data.tar.gz:
|
3
|
+
metadata.gz: 83803766a872ecfb05eeea5ecf9f715ca7cfa0e1
|
4
|
+
data.tar.gz: 43ff5901db1916b48a225a6f5576502c12892002
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: 0020a9532258bf130a8c7b1de8372f09f7b07d03b39f697372b0172b4ed596bee0bce3dfdef169e85fedd413d5f7199727bc6109e8f22c0de34ef4d037f7d1d1
|
7
|
+
data.tar.gz: 3ddb0c339391d19642ce896041fc2e9fa39545f6c2c4413f3bd530d93b16f81b878a604319321b642f4de89264811317eb62dda35f9bf5ea84e1900c3011ff94
|
data/CHANGELOG.md
CHANGED
@@ -1,6 +1,17 @@
|
|
1
1
|
CHANGELOG for ChefSpec
|
2
2
|
======================
|
3
3
|
|
4
|
+
## 3.3.1 (March 11, 2014)
|
5
|
+
Bugfixes:
|
6
|
+
- Various typographical fixes in the README
|
7
|
+
- Remove unused JSON report
|
8
|
+
- Restore coverage reporting for Berkshelf 2 users
|
9
|
+
- Minor formatting changes for errors
|
10
|
+
|
11
|
+
Improvements:
|
12
|
+
- Remove dependency on i18n and use native ERB instead
|
13
|
+
- Vendor Berkshelf/Librarian in a "cookbooks" directory so we can shorten the pathname during coverage reporting
|
14
|
+
|
4
15
|
## 3.3.0 (March 9, 2014)
|
5
16
|
Bugfixes:
|
6
17
|
- Update documentation for setting `automatic` attributes
|
data/README.md
CHANGED
@@ -550,7 +550,7 @@ end
|
|
550
550
|
|
551
551
|
Reporting
|
552
552
|
---------
|
553
|
-
ChefSpec can generate a report of resources read over resources tested.
|
553
|
+
ChefSpec can generate a report of resources read over resources tested.
|
554
554
|
|
555
555
|
To generate the coverage report, add the following to your `spec_helper.rb` before you require any "Chef" code:
|
556
556
|
|
@@ -564,7 +564,7 @@ ChefSpec::Coverage.start!
|
|
564
564
|
By default, that method will output helpful information to standard out:
|
565
565
|
|
566
566
|
```text
|
567
|
-
ChefSpec Coverage report generated
|
567
|
+
ChefSpec Coverage report generated...
|
568
568
|
|
569
569
|
Total Resources: 6
|
570
570
|
Touched Resources: 1
|
@@ -579,10 +579,6 @@ Untouched Resources:
|
|
579
579
|
package[core] bacon/recipes/default.rb:6
|
580
580
|
```
|
581
581
|
|
582
|
-
It also outputs a machine-parsable JSON file at `.coverage/results.json`. This file can be read by your CI server to determine changes in code coverage. We recommend adding the `.coverage` directory to your `.gitignore` to avoid committing it to git.
|
583
|
-
|
584
|
-
You can configure both the announcing behavior and JSON file. Please see the YARD documentation for more information.
|
585
|
-
|
586
582
|
By default, ChefSpec will test all cookbooks that are loaded as part of the Chef Client run. If you have a cookbook with many dependencies, this may be less than desireable. To restrict coverage reporting against certain cookbooks, `ChefSpec::Coverage` yields a block:
|
587
583
|
|
588
584
|
```ruby
|
@@ -876,7 +872,7 @@ expect(chef_run).to include_recipe('bacon::default')
|
|
876
872
|
Assert that the correct attribute is used:
|
877
873
|
|
878
874
|
```ruby
|
879
|
-
expect(
|
875
|
+
expect(chef_run.node['bacon']['temperature']).to eq(150)
|
880
876
|
```
|
881
877
|
|
882
878
|
**NOTE** If your roles live somewhere outside of the expected path, you must set `RSpec.config.role_path` to point to the directory containing your roles **before** invoking the `#converge` method!
|
data/chefspec.gemspec
CHANGED
@@ -29,7 +29,6 @@ Gem::Specification.new do |s|
|
|
29
29
|
s.add_dependency 'chef', '~> 11.0'
|
30
30
|
s.add_dependency 'fauxhai', '~> 2.0'
|
31
31
|
s.add_dependency 'rspec', '~> 2.14'
|
32
|
-
s.add_dependency 'i18n', '>= 0.6.9', '< 1.0.0'
|
33
32
|
|
34
33
|
# Development Dependencies
|
35
34
|
s.add_development_dependency 'chef-zero', '~> 1.7'
|
data/lib/chefspec.rb
CHANGED
data/lib/chefspec/berkshelf.rb
CHANGED
@@ -23,19 +23,23 @@ module ChefSpec
|
|
23
23
|
def setup!
|
24
24
|
berksfile = ::Berkshelf::Berksfile.from_file('Berksfile')
|
25
25
|
|
26
|
+
# Grab a handle to tmpdir, since Berkshelf 2 modifies it a bit
|
27
|
+
tmpdir = File.join(@tmpdir, 'cookbooks')
|
28
|
+
|
26
29
|
::Berkshelf.ui.mute do
|
27
30
|
if ::Berkshelf::Berksfile.method_defined?(:vendor)
|
28
|
-
|
29
|
-
|
31
|
+
# Berkshelf 3.0 requires the directory to not exist
|
32
|
+
FileUtils.rm_rf(tmpdir)
|
33
|
+
berksfile.vendor(tmpdir)
|
30
34
|
else
|
31
|
-
berksfile.install(path:
|
35
|
+
berksfile.install(path: tmpdir)
|
32
36
|
end
|
33
37
|
end
|
34
38
|
|
35
39
|
filter = Coverage::BerkshelfFilter.new(berksfile)
|
36
40
|
Coverage.add_filter(filter)
|
37
41
|
|
38
|
-
::RSpec.configure { |config| config.cookbook_path =
|
42
|
+
::RSpec.configure { |config| config.cookbook_path = tmpdir }
|
39
43
|
end
|
40
44
|
|
41
45
|
#
|
data/lib/chefspec/coverage.rb
CHANGED
@@ -34,9 +34,9 @@ module ChefSpec
|
|
34
34
|
# Start the coverage reporting analysis. This method also adds the the
|
35
35
|
# +at_exit+ handler for printing the coverage report.
|
36
36
|
#
|
37
|
-
def start!(
|
37
|
+
def start!(&block)
|
38
38
|
instance_eval(&block) if block
|
39
|
-
at_exit { ChefSpec::Coverage.report!
|
39
|
+
at_exit { ChefSpec::Coverage.report! }
|
40
40
|
end
|
41
41
|
|
42
42
|
#
|
@@ -110,17 +110,7 @@ module ChefSpec
|
|
110
110
|
#
|
111
111
|
# ChefSpec::Coverage.report!
|
112
112
|
#
|
113
|
-
|
114
|
-
#
|
115
|
-
# ChefSpec::Coverage.report!('/custom/path', false)
|
116
|
-
#
|
117
|
-
#
|
118
|
-
# @param [String] output
|
119
|
-
# the path to output the report on disk (default: '.coverage/results.json')
|
120
|
-
# @param [Boolean] announce
|
121
|
-
# print the results to standard out
|
122
|
-
#
|
123
|
-
def report!(output = '.coverage/results.json', announce = true)
|
113
|
+
def report!
|
124
114
|
# Borrowed from simplecov#41
|
125
115
|
#
|
126
116
|
# If an exception is thrown that isn't a "SystemExit", we need to capture
|
@@ -131,55 +121,19 @@ module ChefSpec
|
|
131
121
|
exit_status = EXIT_SUCCESS
|
132
122
|
end
|
133
123
|
|
134
|
-
report = {}
|
135
|
-
|
136
|
-
|
137
|
-
|
138
|
-
if report[:total] == 0
|
139
|
-
puts 'No resources found, skipping coverage calculation'
|
140
|
-
return
|
124
|
+
report = {}.tap do |h|
|
125
|
+
h[:total] = @collection.size
|
126
|
+
h[:touched] = @collection.count { |_, resource| resource.touched? }
|
127
|
+
h[:coverage] = ((h[:touched]/h[:total].to_f)*100).round(2)
|
141
128
|
end
|
142
129
|
|
143
|
-
report[:
|
144
|
-
|
145
|
-
|
146
|
-
|
147
|
-
report[:detailed] = Hash[*@collection.map do |name, wrapper|
|
148
|
-
[name, wrapper.to_hash]
|
149
|
-
end.flatten]
|
150
|
-
|
151
|
-
output = File.expand_path(output)
|
152
|
-
FileUtils.mkdir_p(File.dirname(output))
|
153
|
-
File.open(File.join(output), 'w') do |f|
|
154
|
-
f.write(JSON.pretty_generate(report) + "\n")
|
155
|
-
end
|
130
|
+
report[:untouched_resources] = @collection.collect do |_, resource|
|
131
|
+
resource unless resource.touched?
|
132
|
+
end.compact
|
156
133
|
|
157
|
-
|
158
|
-
|
159
|
-
|
160
|
-
WARNING: ChefSpec Coverage reporting is in beta. Please use with caution.
|
161
|
-
|
162
|
-
ChefSpec Coverage report generated at '#{output}':
|
163
|
-
|
164
|
-
Total Resources: #{report[:total]}
|
165
|
-
Touched Resources: #{report[:touched]}
|
166
|
-
Touch Coverage: #{report[:coverage]}%
|
167
|
-
|
168
|
-
Untouched Resources:
|
169
|
-
|
170
|
-
#{
|
171
|
-
report[:detailed]
|
172
|
-
.select { |_, resource| !resource[:touched] }
|
173
|
-
.sort_by { |_, resource| [resource[:source][:file], resource[:source][:line]] }
|
174
|
-
.map do |name, resource|
|
175
|
-
" #{name.ljust(32)} #{resource[:source][:file]}:#{resource[:source][:line]}"
|
176
|
-
end
|
177
|
-
.flatten
|
178
|
-
.join("\n")
|
179
|
-
}
|
180
|
-
|
181
|
-
EOH
|
182
|
-
end
|
134
|
+
template = ChefSpec.root.join('templates', 'coverage', 'human.erb')
|
135
|
+
erb = Erubis::Eruby.new(File.read(template))
|
136
|
+
puts erb.evaluate(report)
|
183
137
|
|
184
138
|
# Ensure we exit correctly (#351)
|
185
139
|
exit(exit_status)
|
@@ -206,21 +160,12 @@ module ChefSpec
|
|
206
160
|
@resource.to_s
|
207
161
|
end
|
208
162
|
|
209
|
-
def
|
210
|
-
|
211
|
-
file, line, *_ = @resource.source_line.split(':')
|
212
|
-
|
213
|
-
{
|
214
|
-
file: shortname(file),
|
215
|
-
line: line.to_i,
|
216
|
-
}
|
163
|
+
def source_file
|
164
|
+
@source_file ||= shortname(@resource.source_line.split(':').first)
|
217
165
|
end
|
218
166
|
|
219
|
-
def
|
220
|
-
|
221
|
-
source: source,
|
222
|
-
touched: touched?,
|
223
|
-
}
|
167
|
+
def source_line
|
168
|
+
@source_line ||= @resource.source_line.split(':', 2).last.to_i
|
224
169
|
end
|
225
170
|
|
226
171
|
def touch!
|
@@ -6,7 +6,7 @@ module ChefSpec
|
|
6
6
|
end
|
7
7
|
|
8
8
|
def matches?
|
9
|
-
|
9
|
+
raise RuntimeError, "Must override Filter#matches?"
|
10
10
|
end
|
11
11
|
end
|
12
12
|
|
@@ -50,7 +50,17 @@ module ChefSpec
|
|
50
50
|
class BerkshelfFilter < Filter
|
51
51
|
def initialize(berksfile)
|
52
52
|
@berksfile = berksfile
|
53
|
-
|
53
|
+
|
54
|
+
@metadatas = if berksfile.respond_to?(:dependencies)
|
55
|
+
berksfile.dependencies
|
56
|
+
.select(&:metadata?)
|
57
|
+
.map(&:name)
|
58
|
+
else
|
59
|
+
berksfile.sources.select(&:location)
|
60
|
+
.map(&:location)
|
61
|
+
.select(&:metadata?)
|
62
|
+
.map(&:name)
|
63
|
+
end
|
54
64
|
end
|
55
65
|
|
56
66
|
def matches?(resource)
|
data/lib/chefspec/errors.rb
CHANGED
@@ -3,9 +3,11 @@ module ChefSpec
|
|
3
3
|
class ChefSpecError < StandardError
|
4
4
|
def initialize(options = {})
|
5
5
|
class_name = self.class.to_s.split('::').last
|
6
|
-
|
6
|
+
filename = options.delete(:_template) || Util.underscore(class_name)
|
7
|
+
template = ChefSpec.root.join('templates', 'errors', "#{filename}.erb")
|
7
8
|
|
8
|
-
|
9
|
+
erb = Erubis::Eruby.new(File.read(template))
|
10
|
+
super erb.evaluate(options)
|
9
11
|
end
|
10
12
|
end
|
11
13
|
|
@@ -19,10 +21,10 @@ module ChefSpec
|
|
19
21
|
signature = "#{type}(#{options[:args].map(&:inspect).join(', ')})"
|
20
22
|
|
21
23
|
super({
|
22
|
-
type:
|
23
|
-
signature:
|
24
|
-
stub:
|
25
|
-
|
24
|
+
type: type,
|
25
|
+
signature: signature,
|
26
|
+
stub: stub,
|
27
|
+
_template: :not_stubbed,
|
26
28
|
}.merge(options))
|
27
29
|
end
|
28
30
|
end
|
data/lib/chefspec/version.rb
CHANGED
@@ -0,0 +1,57 @@
|
|
1
|
+
require 'spec_helper'
|
2
|
+
|
3
|
+
module ChefSpec::Error
|
4
|
+
describe CommandNotStubbed do
|
5
|
+
let(:instance) { described_class.new(args: ['cat']) }
|
6
|
+
|
7
|
+
it 'raises an exception with the correct message' do
|
8
|
+
instance
|
9
|
+
expect { raise instance }.to raise_error { |error|
|
10
|
+
expect(error).to be_a(described_class)
|
11
|
+
expect(error.message).to eq <<-EOH.gsub(/^ {10}/, '')
|
12
|
+
Executing a real command is disabled. Unregistered command:
|
13
|
+
|
14
|
+
command("cat")
|
15
|
+
|
16
|
+
You can stub this command with:
|
17
|
+
|
18
|
+
stub_command("cat").and_return(...)
|
19
|
+
EOH
|
20
|
+
}
|
21
|
+
end
|
22
|
+
end
|
23
|
+
|
24
|
+
describe CookbookPathNotFound do
|
25
|
+
let(:instance) { described_class.new }
|
26
|
+
|
27
|
+
it 'raises an exception with the correct message' do
|
28
|
+
expect { raise instance }.to raise_error { |error|
|
29
|
+
expect(error).to be_a(described_class)
|
30
|
+
expect(error.message).to eq <<-EOH.gsub(/^ {10}/, '')
|
31
|
+
I could not find or infer a cookbook_path from your current working directory.
|
32
|
+
Please make sure you put your specs (tests) under a directory named 'spec' or
|
33
|
+
manually set the cookbook path in the RSpec configuration.
|
34
|
+
EOH
|
35
|
+
}
|
36
|
+
end
|
37
|
+
end
|
38
|
+
|
39
|
+
describe GemLoadError do
|
40
|
+
let(:instance) { described_class.new(gem: 'bacon', name: 'bacon') }
|
41
|
+
|
42
|
+
it 'raises an exception with the correct message' do
|
43
|
+
expect { raise instance }.to raise_error { |error|
|
44
|
+
expect(error).to be_a(described_class)
|
45
|
+
expect(error.message).to eq <<-EOH.gsub(/^ {10}/, '')
|
46
|
+
I could not load the 'bacon' gem! You must have the gem installed
|
47
|
+
on your local system before you can use the bacon plugin.
|
48
|
+
You can install bacon by running:
|
49
|
+
|
50
|
+
gem install bacon
|
51
|
+
|
52
|
+
or add bacon to your Gemfile and run the `bundle` command to install.
|
53
|
+
EOH
|
54
|
+
}
|
55
|
+
end
|
56
|
+
end
|
57
|
+
end
|
@@ -0,0 +1,22 @@
|
|
1
|
+
|
2
|
+
<% if @total == 0 %>
|
3
|
+
No Chef resources found, skipping coverage calculation...
|
4
|
+
<% else %>
|
5
|
+
ChefSpec Coverage report generated...
|
6
|
+
|
7
|
+
Total Resources: <%= @total %>
|
8
|
+
Touched Resources: <%= @touched %>
|
9
|
+
Touch Coverage: <%= @coverage %>%
|
10
|
+
|
11
|
+
<% if @untouched_resources.empty? %>
|
12
|
+
You are awesome and so is your test coverage! Have a fantastic day!
|
13
|
+
|
14
|
+
<% else %>
|
15
|
+
Untouched Resources:
|
16
|
+
|
17
|
+
<% @untouched_resources.each do |resource| %>
|
18
|
+
<%= resource.to_s.ljust(32) %> <%= resource.source_file %>:<%= resource.source_line %>
|
19
|
+
<% end %>
|
20
|
+
|
21
|
+
<% end %>
|
22
|
+
<% end %>
|
@@ -0,0 +1,7 @@
|
|
1
|
+
I could not load the '<%= @name %>' gem! You must have the gem installed
|
2
|
+
on your local system before you can use the <%= @gem %> plugin.
|
3
|
+
You can install <%= @gem %> by running:
|
4
|
+
|
5
|
+
gem install <%= @gem %>
|
6
|
+
|
7
|
+
or add <%= @name %> to your Gemfile and run the `bundle` command to install.
|
metadata
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: chefspec
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 3.3.
|
4
|
+
version: 3.3.1
|
5
5
|
platform: ruby
|
6
6
|
authors:
|
7
7
|
- Andrew Crump
|
@@ -9,7 +9,7 @@ authors:
|
|
9
9
|
autorequire:
|
10
10
|
bindir: bin
|
11
11
|
cert_chain: []
|
12
|
-
date: 2014-03-
|
12
|
+
date: 2014-03-11 00:00:00.000000000 Z
|
13
13
|
dependencies:
|
14
14
|
- !ruby/object:Gem::Dependency
|
15
15
|
name: chef
|
@@ -53,26 +53,6 @@ dependencies:
|
|
53
53
|
- - "~>"
|
54
54
|
- !ruby/object:Gem::Version
|
55
55
|
version: '2.14'
|
56
|
-
- !ruby/object:Gem::Dependency
|
57
|
-
name: i18n
|
58
|
-
requirement: !ruby/object:Gem::Requirement
|
59
|
-
requirements:
|
60
|
-
- - ">="
|
61
|
-
- !ruby/object:Gem::Version
|
62
|
-
version: 0.6.9
|
63
|
-
- - "<"
|
64
|
-
- !ruby/object:Gem::Version
|
65
|
-
version: 1.0.0
|
66
|
-
type: :runtime
|
67
|
-
prerelease: false
|
68
|
-
version_requirements: !ruby/object:Gem::Requirement
|
69
|
-
requirements:
|
70
|
-
- - ">="
|
71
|
-
- !ruby/object:Gem::Version
|
72
|
-
version: 0.6.9
|
73
|
-
- - "<"
|
74
|
-
- !ruby/object:Gem::Version
|
75
|
-
version: 1.0.0
|
76
56
|
- !ruby/object:Gem::Dependency
|
77
57
|
name: chef-zero
|
78
58
|
requirement: !ruby/object:Gem::Requirement
|
@@ -731,11 +711,11 @@ files:
|
|
731
711
|
- lib/chefspec/stubs/stub.rb
|
732
712
|
- lib/chefspec/util.rb
|
733
713
|
- lib/chefspec/version.rb
|
734
|
-
- locales/en.yml
|
735
714
|
- spec/spec_helper.rb
|
736
715
|
- spec/support/hash.rb
|
737
716
|
- spec/unit/api_spec.rb
|
738
717
|
- spec/unit/cacher_spec.rb
|
718
|
+
- spec/unit/errors_spec.rb
|
739
719
|
- spec/unit/expect_exception_spec.rb
|
740
720
|
- spec/unit/extensions/lwrp_base_spec.rb
|
741
721
|
- spec/unit/macros_spec.rb
|
@@ -758,6 +738,10 @@ files:
|
|
758
738
|
- spec/unit/stubs/search_registry_spec.rb
|
759
739
|
- spec/unit/stubs/search_stub_spec.rb
|
760
740
|
- spec/unit/stubs/stub_spec.rb
|
741
|
+
- templates/coverage/human.erb
|
742
|
+
- templates/errors/cookbook_path_not_found.erb
|
743
|
+
- templates/errors/gem_load_error.erb
|
744
|
+
- templates/errors/not_stubbed.erb
|
761
745
|
homepage: http://code.sethvargo.com/chefspec
|
762
746
|
licenses:
|
763
747
|
- MIT
|
@@ -858,6 +842,7 @@ test_files:
|
|
858
842
|
- spec/support/hash.rb
|
859
843
|
- spec/unit/api_spec.rb
|
860
844
|
- spec/unit/cacher_spec.rb
|
845
|
+
- spec/unit/errors_spec.rb
|
861
846
|
- spec/unit/expect_exception_spec.rb
|
862
847
|
- spec/unit/extensions/lwrp_base_spec.rb
|
863
848
|
- spec/unit/macros_spec.rb
|
data/locales/en.yml
DELETED
@@ -1,19 +0,0 @@
|
|
1
|
-
en:
|
2
|
-
chefspec:
|
3
|
-
errors:
|
4
|
-
cookbook_path_not_found: >
|
5
|
-
I could not find or infer a `cookbook_path' from your current working
|
6
|
-
directory. Please make sure you put your specs (tests) under a directory
|
7
|
-
named `spec' or manually set the cookbook path in the RSpec
|
8
|
-
configuration.
|
9
|
-
gem_load_error: >
|
10
|
-
I could not load the %{name} gem! You must have %{name} installed on
|
11
|
-
your local system before you can use the `%{gem}' plugin. You can
|
12
|
-
install %{gem} by running `gem install %{gem}', or add %{name} to your
|
13
|
-
Gemfile and run the `bundle' command to install.
|
14
|
-
not_stubbed: |-
|
15
|
-
Executing a real %{type} is disabled. Unregistered %{type}: `%{signature}`"
|
16
|
-
|
17
|
-
You can stub this %{type} with:
|
18
|
-
|
19
|
-
%{stub}
|