chef-gen-flavors 0.6.2 → 0.7.0

Sign up to get free protection for your applications and to get access to all the features.
Files changed (74) hide show
  1. checksums.yaml +4 -4
  2. data/ARUBA_STEPS.md +74 -0
  3. data/History.md +16 -0
  4. data/Manifest.txt +25 -30
  5. data/README.md +121 -16
  6. data/chef-gen-flavors.gemspec +8 -5
  7. data/lib/chef_gen/flavor_base.rb +42 -34
  8. data/lib/chef_gen/flavors.rb +36 -10
  9. data/lib/chef_gen/snippet/attributes.rb +13 -0
  10. data/lib/chef_gen/snippet/chef_spec.rb +84 -14
  11. data/lib/chef_gen/snippet/cookbook_base.rb +109 -23
  12. data/lib/chef_gen/snippet/example_file.rb +15 -0
  13. data/lib/chef_gen/snippet/example_template.rb +15 -0
  14. data/lib/chef_gen/snippet/git_init.rb +2 -0
  15. data/lib/chef_gen/snippet/recipes.rb +15 -0
  16. data/lib/chef_gen/snippet/resource_provider.rb +18 -0
  17. data/lib/chef_gen/snippet/standard_ignore.rb +56 -80
  18. data/lib/chef_gen/snippet/style_foodcritic.rb +51 -0
  19. data/lib/chef_gen/snippet/style_rubocop.rb +80 -0
  20. data/lib/chef_gen/snippet/style_tailor.rb +48 -0
  21. data/lib/chef_gen/snippet/test_kitchen.rb +70 -15
  22. data/lib/chef_gen/snippets.rb +2 -0
  23. data/shared/snippet/attributes/attributes_default_rb.erb +8 -0
  24. data/{.rspec → shared/snippet/chef_spec/_rspec.erb} +0 -0
  25. data/shared/snippet/chef_spec/spec_chef_runner_context_rb.erb +36 -0
  26. data/shared/snippet/chef_spec/spec_recipes_default_spec_rb.erb +7 -0
  27. data/shared/snippet/chef_spec/spec_spec_helper_rb.erb +95 -0
  28. data/shared/snippet/cookbookbase/Berksfile.erb +5 -0
  29. data/shared/snippet/cookbookbase/CHANGELOG_md.erb +5 -0
  30. data/shared/snippet/cookbookbase/Gemfile.erb +7 -0
  31. data/shared/snippet/cookbookbase/Guardfile.erb +10 -0
  32. data/shared/snippet/cookbookbase/README_md.erb +92 -0
  33. data/shared/snippet/cookbookbase/Rakefile.erb +20 -0
  34. data/shared/snippet/cookbookbase/metadata_rb.erb +10 -0
  35. data/shared/snippet/examplefile/files_default_example_conf +34 -0
  36. data/shared/snippet/exampletemplate/templates_default_example_conf_erb +22 -0
  37. data/shared/snippet/recipes/recipes_default_rb.erb +9 -0
  38. data/shared/snippet/resourceprovider/providers_default_rb.erb +20 -0
  39. data/shared/snippet/resourceprovider/resources_default_rb.erb +9 -0
  40. data/shared/snippet/stylerubocop/_rubocop_yml.erb +27 -0
  41. data/shared/snippet/testkitchen/_kitchen_yml.erb +30 -0
  42. data/shared/snippet/testkitchen/libraries_kitchen_helper_rb +13 -0
  43. data/shared/snippet/testkitchen/test_integration_default_serverspec_recipes_default_spec_rb.erb +16 -0
  44. data/shared/snippet/testkitchen/test_integration_default_serverspec_spec_helper_rb.erb +7 -0
  45. metadata +42 -32
  46. data/.rubocop.yml +0 -27
  47. data/.travis.yml +0 -6
  48. data/Gemfile +0 -3
  49. data/Guardfile +0 -15
  50. data/Rakefile +0 -98
  51. data/features/generate.feature +0 -17
  52. data/features/support/env.rb +0 -15
  53. data/spec/lib/chef_gen/flavor_base_spec.rb +0 -167
  54. data/spec/lib/chef_gen/flavors_spec.rb +0 -132
  55. data/spec/lib/chef_gen/snippet/attributes_spec.rb +0 -40
  56. data/spec/lib/chef_gen/snippet/chef_spec_spec.rb +0 -40
  57. data/spec/lib/chef_gen/snippet/cookbook_base_spec.rb +0 -32
  58. data/spec/lib/chef_gen/snippet/example_file_spec.rb +0 -40
  59. data/spec/lib/chef_gen/snippet/example_template_spec.rb +0 -40
  60. data/spec/lib/chef_gen/snippet/git_init_spec.rb +0 -30
  61. data/spec/lib/chef_gen/snippet/recipes_spec.rb +0 -40
  62. data/spec/lib/chef_gen/snippet/resource_provider_spec.rb +0 -40
  63. data/spec/lib/chef_gen/snippet/standard_ignore_spec.rb +0 -35
  64. data/spec/lib/chef_gen/snippet/style_rubocop_spec.rb +0 -31
  65. data/spec/lib/chef_gen/snippet/test_kitchen_spec.rb +0 -44
  66. data/spec/spec_helper.rb +0 -64
  67. data/spec/support/fixtures/code_generator/metadata.rb +0 -2
  68. data/spec/support/fixtures/code_generator/recipes/cookbook.rb +0 -1
  69. data/spec/support/fixtures/code_generator_2/metadata.rb +0 -2
  70. data/spec/support/fixtures/code_generator_2/recipes/cookbook.rb +0 -3
  71. data/spec/support/fixtures/code_generator_2/templates/default/README_md.erb +0 -1
  72. data/spec/support/fixtures/lib/chef_gen/flavor/bar.rb +0 -21
  73. data/spec/support/fixtures/lib/chef_gen/flavor/baz.rb +0 -6
  74. data/spec/support/fixtures/lib/chef_gen/flavor/foo.rb +0 -9
@@ -8,7 +8,7 @@ module ChefGen
8
8
  # a plugin framework for creating ChefDK generator flavors
9
9
  class Flavors
10
10
  # the version of the gem
11
- VERSION = '0.6.2'
11
+ VERSION = '0.7.0'
12
12
 
13
13
  extend LittlePlugger path: 'chef_gen/flavor',
14
14
  module: ChefGen::Flavor
@@ -18,7 +18,7 @@ module ChefGen
18
18
  # for the selected ChefGen Flavor
19
19
  # @return [String] the path to the code_generator cookbook
20
20
  def path
21
- # then take a copy so we can augment it
21
+ # select the plugin to use
22
22
  @plugins = plugins.dup
23
23
  add_builtin_template
24
24
  selected = plugin_from_env ||
@@ -27,13 +27,27 @@ module ChefGen
27
27
  fail('no ChefGen flavors found!')
28
28
  path = generator_path(selected)
29
29
  $stdout.puts "using ChefGen flavor '#{selected}' in #{path}"
30
- copy = copy_generator_dir(path, selected)
31
- ChefDK::Generator.add_attr_to_context('generator_path', copy)
30
+ # take a copy so we can augment it
31
+ copy = copy_generator_dir(path)
32
+ # augment the copy if the plugin has hooks
33
+ run_content_hooks(selected, copy)
34
+ # return the path to the copy
32
35
  copy
33
36
  end
34
37
 
35
38
  private
36
39
 
40
+ # call content hooks in the flavor if it has any
41
+ # @param selected [Symbol] the selected flavor
42
+ # @param path [String] the temporary generator cookbook path
43
+ # @return [void]
44
+ def run_content_hooks(selected, path)
45
+ flavor_klass = @plugins[selected]
46
+ return unless flavor_klass.is_a?(Class)
47
+ return unless flavor_klass.instance_methods.include?(:add_content)
48
+ @plugins[selected].new(nil).add_content(path)
49
+ end
50
+
37
51
  # checks if the plugin to use has been specified in the environment
38
52
  # variable CHEFGEN_FLAVOR
39
53
  # @return [Symbol,nil] the plugin if specified and found, nil otherwise
@@ -94,15 +108,25 @@ module ChefGen
94
108
  if true == klass
95
109
  output << "#{idx}. ChefDK built-in template"
96
110
  else
97
- descr = klass.respond_to?(:description) ? klass.description : ''
98
- version = klass.const_defined?(:VERSION) ? "v#{klass.const_get(:VERSION, false)}" : ''
99
- output << "#{idx}. #{name}: #{descr} #{version}"
111
+ output << "#{idx}. #{name}: #{plugin_descr(klass)}"
100
112
  end
101
113
  idx += 1
102
114
  end
103
115
  ui.info "#{output.join("\n")}\n"
104
116
  valid
105
117
  end
118
+
119
+ # builds the description of a flavor for the menu
120
+ # @param klass [Class] the class of the flavor
121
+ # @return [String] the flavor description with version if available
122
+ def plugin_descr(klass)
123
+ descr = klass.respond_to?(:description) ? klass.description : ''
124
+ if klass.const_defined?(:VERSION)
125
+ descr += " v#{klass.const_get(:VERSION, false)}"
126
+ end
127
+ descr
128
+ end
129
+
106
130
  # :nocov:
107
131
 
108
132
  # returns the path to the code_generator cookbook for the
@@ -167,11 +191,13 @@ module ChefGen
167
191
  # in the environment.
168
192
  # @param srcdir [String] the path to the generator cookbook
169
193
  # @return [String] the temporary path to generate from
170
- def copy_generator_dir(srcdir, selected)
194
+ def copy_generator_dir(srcdir)
171
195
  dstdir = Dir.mktmpdir('chefgen_flavor.')
172
- at_exit {
196
+ at_exit do
173
197
  FileUtils.rm_rf(dstdir)
174
- } unless ENV.key?('CHEFGEN_NOCLEANTMP')
198
+ end unless ENV.key?('CHEFGEN_NOCLEANTMP')
199
+ $stdout.puts srcdir
200
+ $stdout.puts dstdir
175
201
  FileUtils.cp_r(srcdir, dstdir)
176
202
  File.join(dstdir, File.basename(srcdir))
177
203
  end
@@ -17,6 +17,19 @@ module ChefGen
17
17
  def snippet_attributes_files(recipe)
18
18
  @templates_if_missing << File.join('attributes', 'default.rb')
19
19
  end
20
+
21
+ # copies snippet content
22
+ # @param path [String] the path to the temporary generator cookbook
23
+ # @return [void]
24
+ def content_attribute_files(path)
25
+ copy_snippet_file(
26
+ File.join(
27
+ File.dirname(__FILE__), '..', '..', '..',
28
+ 'shared', 'snippet', 'attributes', 'attributes_default_rb.erb'
29
+ ),
30
+ File.join(path, 'templates', 'default', 'attributes_default_rb.erb')
31
+ )
32
+ end
20
33
  end
21
34
  end
22
35
  end
@@ -2,39 +2,109 @@ module ChefGen
2
2
  module Snippet
3
3
  # creates a framework for ChefSpec unit testing
4
4
  module ChefSpec
5
- # declares the .rspec file
5
+ # declares directories
6
6
  # @param recipe [Chef::Recipe] the recipe into which resources
7
7
  # will be injected
8
8
  # @return [void]
9
- def snippet_chefspec_dotrspec(recipe)
9
+ def snippet_chefspec_dirs(recipe)
10
+ @directories << 'spec'
11
+ @directories << File.join('spec', 'recipes')
12
+ end
13
+
14
+ # declares files
15
+ # @param recipe [Chef::Recipe] the recipe into which resources
16
+ # will be injected
17
+ # @return [void]
18
+ def snippet_chefspec_files(recipe)
10
19
  @templates << '.rspec'
20
+ @templates_if_missing << File.join('spec', 'spec_helper.rb')
21
+ @templates_if_missing << File.join('spec', 'recipes', 'default_spec.rb')
22
+ @templates_if_missing << File.join('spec', 'chef_runner_context.rb')
11
23
  end
12
24
 
13
- # declares the ChefSpec directories
25
+ # adds chefspec files to the git and chefignore patterns
14
26
  # @param recipe [Chef::Recipe] the recipe into which resources
15
27
  # will be injected
16
28
  # @return [void]
17
- def snippet_chefspec_dirs(recipe)
18
- @directories << 'spec'
19
- @directories << File.join('spec', 'recipes')
29
+ def snippet_chefspec_ignore(recipe)
30
+ return unless respond_to?(:chefignore_patterns)
31
+ %w(
32
+ .rspec
33
+ spec/*
34
+ spec/fixtures/*
35
+ ).each do |e|
36
+ chefignore_patterns << e
37
+ end
20
38
  end
21
39
 
22
- # declares the ChefSpec spec_helper
40
+ # adds chefspec gems to the Gemfile
23
41
  # @param recipe [Chef::Recipe] the recipe into which resources
24
42
  # will be injected
25
43
  # @return [void]
26
- def snippet_chefspec_spechelper(recipe)
27
- @templates_if_missing << File.join('spec', 'spec_helper.rb')
44
+ def snippet_chefspec_gems(recipe)
45
+ return unless respond_to?(:cookbook_gems)
46
+ cookbook_gems['chefspec'] = '~> 4.1'
47
+ cookbook_gems['guard-rspec'] = '~> 4.5'
48
+ cookbook_gems['ci_reporter_rspec'] = '~> 1.0'
49
+ end
50
+
51
+ # adds chefspec rake tasks to the Rakefile
52
+ # @param recipe [Chef::Recipe] the recipe into which resources
53
+ # will be injected
54
+ # @return [void]
55
+ def snippet_chefspec_raketasks(recipe)
56
+ return unless respond_to?(:rake_tasks)
57
+ rake_tasks['chefspec'] = <<'END'
58
+ require 'rspec/core/rake_task'
59
+ RSpec::Core::RakeTask.new(:chefspec)
60
+
61
+ desc 'Generate ChefSpec coverage report'
62
+ task :coverage do
63
+ ENV['COVERAGE'] = 'true'
64
+ Rake::Task[:chefspec].invoke
65
+ end
66
+ task spec: :chefspec
67
+ END
28
68
  end
29
69
 
30
- # declares the default recipe spec
70
+ # adds chefspec sets to the Guardfile
31
71
  # @param recipe [Chef::Recipe] the recipe into which resources
32
72
  # will be injected
33
73
  # @return [void]
34
- def snippet_chefspec_defaultrecipespec(recipe)
35
- @templates_if_missing << File.join(
36
- 'spec', 'recipes', 'default_spec.rb'
37
- )
74
+ def snippet_chefspec_guardsets(recipe)
75
+ return unless respond_to?(:guard_sets)
76
+ guard_sets['chefspec'] = <<'END'
77
+ rspec_command = ENV.key?('DISABLE_PRY_RESCUE') ? 'rspec' : 'rescue rspec'
78
+ guard :rspec, all_on_start: true, cmd: "bundle exec #{rspec_command}" do
79
+ watch(%r{^spec/recipes/.+_spec\.rb$})
80
+ watch(%r{^spec/spec_helper\.rb$}) { 'spec' }
81
+ watch(%r{^attributes/.+\.rb$}) { 'spec' }
82
+ watch(%r{^resources/.+\.rb$}) { 'spec' }
83
+ watch(%r{^providers/.+\.rb$}) { 'spec' }
84
+ watch(%r{^libraries/.+\.rb$}) { 'spec' }
85
+ watch(%r{^recipes/(.+)\.rb$}) { |m| "spec/recipes/#{m[1]}_spec.rb" }
86
+ end
87
+ END
88
+ end
89
+
90
+ # copies snippet content
91
+ # @param path [String] the path to the temporary generator cookbook
92
+ # @return [void]
93
+ def content_chefspec_files(path)
94
+ %w(
95
+ _rspec.erb
96
+ spec_spec_helper_rb.erb
97
+ spec_recipes_default_spec_rb.erb
98
+ spec_chef_runner_context_rb.erb
99
+ ).each do |file|
100
+ copy_snippet_file(
101
+ File.join(
102
+ File.dirname(__FILE__), '..', '..', '..',
103
+ 'shared', 'snippet', 'chef_spec', file
104
+ ),
105
+ File.join(path, 'templates', 'default', file)
106
+ )
107
+ end
38
108
  end
39
109
  end
40
110
  end
@@ -1,63 +1,149 @@
1
+ # rubocop:disable Metrics/MethodLength
2
+
1
3
  module ChefGen
2
4
  module Snippet
3
5
  # creates the basic files that every cookbook should have
4
6
  # each file is managed through a separate method to allow for
5
7
  # people to mix this in but turn off just one file
6
8
  module CookbookBase
7
- # declares the Gemfile
9
+ # adds a Hash for gems to add to the gemfile
10
+ attr_reader :cookbook_gems
11
+
12
+ # adds an Array of gem sources, defaulting to rubygems
13
+ attr_reader :gem_sources
14
+
15
+ # adds an Array of berks sources, defaulting to supermarket
16
+ attr_reader :berks_sources
17
+
18
+ # adds a Hash of rake tasks
19
+ attr_reader :rake_tasks
20
+
21
+ # adds a Hash of guard sets
22
+ attr_reader :guard_sets
23
+
24
+ # initializes instance vars
25
+ def init_cookbookbase_instancevars
26
+ @gem_sources = %w(https://rubygems.org)
27
+ @berks_sources = %w(https://supermarket.chef.io)
28
+ @rake_tasks = {}
29
+ @guard_sets = {}
30
+ @cookbook_gems = {
31
+ rake: '~> 10.4',
32
+ pry: '~> 0.10',
33
+ 'pry-byebug' => '~> 3.1',
34
+ 'pry-rescue' => '~> 1.4',
35
+ 'pry-stack_explorer' => '~> 0.4',
36
+ berkshelf: '~> 3.2',
37
+ guard: '~> 2.12'
38
+ }
39
+ end
40
+
41
+ # declares files
8
42
  # @param recipe [Chef::Recipe] the recipe into which resources
9
43
  # will be injected
10
44
  # @return [void]
11
- def snippet_cookbookbase_gemfile(recipe)
12
- @templates << 'Gemfile'
45
+ def snippet_cookbookbase_files(recipe)
46
+ @templates_if_missing << 'metadata.rb'
47
+ @templates_if_missing << 'README.md'
48
+ @templates_if_missing << 'CHANGELOG.md'
13
49
  end
14
50
 
15
- # declares the Berksfile
51
+ # declares the Gemfile with lazy evaluation of the gems
16
52
  # @param recipe [Chef::Recipe] the recipe into which resources
17
53
  # will be injected
18
54
  # @return [void]
19
- def snippet_cookbookbase_berksfile(recipe)
20
- @templates << 'Berksfile'
55
+ def snippet_cookbookbase_gemfile(recipe)
56
+ gems = @cookbook_gems
57
+ sources = @gem_sources
58
+ # :nocov:
59
+ recipe.send(:template, File.join(@target_path, 'Gemfile')) do
60
+ helpers(ChefDK::Generator::TemplateHelper)
61
+ variables lazy { { gems: gems, sources: sources } }
62
+ end
63
+ # :nocov:
21
64
  end
22
65
 
23
- # declares the Rakefile
66
+ # declares the Berksfile with lazy evaluation of the sources
24
67
  # @param recipe [Chef::Recipe] the recipe into which resources
25
68
  # will be injected
26
69
  # @return [void]
27
- def snippet_cookbookbase_rakefile(recipe)
28
- @templates << 'Rakefile'
70
+ def snippet_cookbookbase_berksfile(recipe)
71
+ sources = @berks_sources
72
+ # :nocov:
73
+ recipe.send(:template, File.join(@target_path, 'Berksfile')) do
74
+ helpers(ChefDK::Generator::TemplateHelper)
75
+ variables lazy { { sources: sources } }
76
+ end
77
+ # :nocov:
29
78
  end
30
79
 
31
- # declares the Guardfile
80
+ # declares the Rakefile with lazy evaluation of the tasks
32
81
  # @param recipe [Chef::Recipe] the recipe into which resources
33
82
  # will be injected
34
83
  # @return [void]
35
- def snippet_cookbookbase_guardfile(recipe)
36
- @templates << 'Guardfile'
84
+ def snippet_cookbookbase_rakefile(recipe)
85
+ tasks = @rake_tasks
86
+ # :nocov:
87
+ recipe.send(:template, File.join(@target_path, 'Rakefile')) do
88
+ helpers(ChefDK::Generator::TemplateHelper)
89
+ variables lazy { { tasks: tasks } }
90
+ end
91
+ # :nocov:
37
92
  end
38
93
 
39
- # declares the metadata.rb file
94
+ # declares the Guardfile with lazy evaluation of the guards
40
95
  # @param recipe [Chef::Recipe] the recipe into which resources
41
96
  # will be injected
42
97
  # @return [void]
43
- def snippet_cookbookbase_metadata(recipe)
44
- @templates_if_missing << 'metadata.rb'
98
+ def snippet_cookbookbase_guardfile(recipe)
99
+ guards = @guard_sets
100
+ # :nocov:
101
+ recipe.send(:template, File.join(@target_path, 'Guardfile')) do
102
+ helpers(ChefDK::Generator::TemplateHelper)
103
+ variables lazy { { guards: guards } }
104
+ end
105
+ # :nocov:
45
106
  end
46
107
 
47
- # declares the README file
108
+ # adds base files to the git and chefignore patterns
48
109
  # @param recipe [Chef::Recipe] the recipe into which resources
49
110
  # will be injected
50
111
  # @return [void]
51
- def snippet_cookbookbase_readme(recipe)
52
- @templates_if_missing << 'README.md'
112
+ def snippet_cookbookbase_ignore(recipe)
113
+ return unless respond_to?(:chefignore_patterns)
114
+ %w(
115
+ Gemfile
116
+ Rakefile
117
+ Guardfile
118
+ Berksfile
119
+ ).each do |e|
120
+ chefignore_patterns << e
121
+ end
53
122
  end
54
123
 
55
- # declares the CHANGELOG
56
- # @param recipe [Chef::Recipe] the recipe into which resources
57
- # will be injected
124
+ # copies snippet content
125
+ # @param path [String] the path to the temporary generator cookbook
58
126
  # @return [void]
59
- def snippet_cookbookbase_changelog(recipe)
60
- @templates_if_missing << 'CHANGELOG.md'
127
+ def content_cookbookbase_files(path)
128
+ %w(
129
+ Gemfile.erb
130
+ Berksfile.erb
131
+ Rakefile.erb
132
+ Guardfile.erb
133
+ metadata_rb.erb
134
+ README_md.erb
135
+ CHANGELOG_md.erb
136
+ ).each do |file|
137
+ # :nocov:
138
+ copy_snippet_file(
139
+ File.join(
140
+ File.dirname(__FILE__), '..', '..', '..',
141
+ 'shared', 'snippet', 'cookbookbase', file
142
+ ),
143
+ File.join(path, 'templates', 'default', file)
144
+ )
145
+ # :nocov:
146
+ end
61
147
  end
62
148
  end
63
149
  end
@@ -18,6 +18,21 @@ module ChefGen
18
18
  def snippet_examplefile_files(recipe)
19
19
  @files_if_missing << File.join('files', 'default', 'example.conf')
20
20
  end
21
+
22
+ # copies snippet content
23
+ # @param path [String] the path to the temporary generator cookbook
24
+ # @return [void]
25
+ def content_examplefile_files(path)
26
+ %w(files_default_example_conf).each do |file|
27
+ copy_snippet_file(
28
+ File.join(
29
+ File.dirname(__FILE__), '..', '..', '..',
30
+ 'shared', 'snippet', 'examplefile', file
31
+ ),
32
+ File.join(path, 'files', 'default', file)
33
+ )
34
+ end
35
+ end
21
36
  end
22
37
  end
23
38
  end
@@ -20,6 +20,21 @@ module ChefGen
20
20
  'templates', 'default', 'example.conf.erb'
21
21
  )
22
22
  end
23
+
24
+ # copies snippet content
25
+ # @param path [String] the path to the temporary generator cookbook
26
+ # @return [void]
27
+ def content_exampletemplate_files(path)
28
+ %w(templates_default_example_conf_erb).each do |file|
29
+ copy_snippet_file(
30
+ File.join(
31
+ File.dirname(__FILE__), '..', '..', '..',
32
+ 'shared', 'snippet', 'exampletemplate', file
33
+ ),
34
+ File.join(path, 'files', 'default', file)
35
+ )
36
+ end
37
+ end
23
38
  end
24
39
  end
25
40
  end