chef-workflow-tasklib 0.1.0

Sign up to get free protection for your applications and to get access to all the features.
data/.gitignore ADDED
@@ -0,0 +1,18 @@
1
+ *.gem
2
+ *.rbc
3
+ .bundle
4
+ .config
5
+ .yardoc
6
+ Gemfile.lock
7
+ InstalledFiles
8
+ _yardoc
9
+ coverage
10
+ doc/
11
+ lib/bundler/man
12
+ pkg
13
+ rdoc
14
+ spec/reports
15
+ test/tmp
16
+ test/version_tmp
17
+ tmp
18
+ .chef-workflow
data/Gemfile ADDED
@@ -0,0 +1,4 @@
1
+ source 'https://rubygems.org'
2
+
3
+ # Specify your gem's dependencies in chef-workflow-tasklib.gemspec
4
+ gemspec
data/LICENSE.txt ADDED
@@ -0,0 +1,22 @@
1
+ Copyright (c) 2012 Erik Hollensbe
2
+
3
+ MIT License
4
+
5
+ Permission is hereby granted, free of charge, to any person obtaining
6
+ a copy of this software and associated documentation files (the
7
+ "Software"), to deal in the Software without restriction, including
8
+ without limitation the rights to use, copy, modify, merge, publish,
9
+ distribute, sublicense, and/or sell copies of the Software, and to
10
+ permit persons to whom the Software is furnished to do so, subject to
11
+ the following conditions:
12
+
13
+ The above copyright notice and this permission notice shall be
14
+ included in all copies or substantial portions of the Software.
15
+
16
+ THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
17
+ EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
18
+ MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
19
+ NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
20
+ LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
21
+ OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
22
+ WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
data/README.md ADDED
@@ -0,0 +1,260 @@
1
+ # Chef Workflow - Rake Tasks & Support
2
+
3
+ This gem provides a set of rake tasks broken up logically to support a chef
4
+ workflow, and tooling to assist with driving those tasks. It is intended to
5
+ complement a chef repository by directly being added as a dependency.
6
+
7
+ Some of the tasks it provides are:
8
+
9
+ * Uploading your cookbooks, roles, environments and databags with the defaults
10
+ expecting a layout similar to the [opscode example
11
+ chef-repo](https://github.com/opscode/chef-repo)
12
+ * Resolving your cookbook's dependencies, with tools like
13
+ [librarian](https://github.com/applicationsonline/librarian) or
14
+ [berkshelf](https://github.com/RiotGames/berkshelf)
15
+ * Lint your cookbooks with [foodcritic](https://github.com/acrmp/foodcritic)
16
+ * Creating a chef server for testing in a single command
17
+ * Running unit tests against networks of provisioned machines -- see
18
+ [chef-workflow-tasklib](https://github.com/chef-workflow/chef-workflow-testlib)
19
+ for more information.
20
+
21
+ ## We do a lot, but we don't tell you how to do it.
22
+
23
+ The defaults (which you can set up by following the installation instructions)
24
+ use our workflow and a standard chef repository layout. **You don't have to do
25
+ this.** Write your own tasks, use a subset of our tasks, configure our tasks to
26
+ use your settings, or even adjust what happens when you just type `rake`. The
27
+ whole system is built to accomodate this.
28
+
29
+ ## Installation
30
+
31
+ Many of the choices made designing chef-workflow assume bundler is in use. We
32
+ do not recommend installing the gem directly, but through a `Gemfile` that
33
+ lives in your repository.
34
+
35
+ Add this line to your application's Gemfile:
36
+
37
+ gem 'chef-workflow-tasklib'
38
+
39
+ And then execute:
40
+
41
+ $ bundle
42
+
43
+ To get started, run the `chef-workflow-bootstrap` utility which will create
44
+ some files in your repo. It will not overwrite anything.
45
+
46
+ $ bundle exec chef-workflow-bootstrap
47
+
48
+ If you already had a `Rakefile`, it will not be modified. To use the tasks, add
49
+ these two lines to your `Rakefile`:
50
+
51
+ ```ruby
52
+ require 'chef-workflow-tasklib'
53
+ chef_workflow_task 'default'
54
+ ```
55
+
56
+ Then to see all the tasks use:
57
+
58
+ $ bundle exec rake -T
59
+
60
+ **Note:** `rake` by itself will **not work**. We depend on newer gems than the
61
+ `rake` that's included with ruby does, which is what will be used if you do not
62
+ execute `bundle exec rake`. At this point bundler runs, and will fail because
63
+ `rake` will have activated gems that your bundle will be incompatible with.
64
+
65
+ If this is confusing, just remember to always `bundle exec rake` and you won't
66
+ have any trouble.
67
+
68
+ You should see something similar to this:
69
+
70
+ ```
71
+ rake chef:clean # Clean up the state files that chef-workflow generates
72
+ rake chef:clean:ips # Clean up the ip registry for chef-workflow
73
+ rake chef:clean:knife # Clean up the temporary chef configuration for chef-workflow
74
+ rake chef:clean:prisons # Clean up the prison registry for chef-workflow
75
+ rake chef:environments:upload # Upload your environments to the chef server
76
+ rake chef:roles:upload # Upload your roles to the chef server
77
+ rake chef:show_config # Show the calculated configuration for chef-workflow
78
+ rake chef_server:build_knife_config # Create and write a knife configuration suitable for creating new chef servers.
79
+ rake chef_server:create:vagrant # Create a chef server in a vagrant machine.
80
+ rake chef_server:destroy:vagrant # Destroy the last chef server created with vagrant
81
+ rake cookbooks:update # Update your locked cookbooks with Berkshelf
82
+ rake cookbooks:upload # Upload your cookbooks to the chef server
83
+ rake test # Run tests
84
+ rake test:build # test:refresh and test
85
+ rake test:refresh # Refresh all global meta on the chef server
86
+ rake test:vagrant:full # Build a chef server with vagrant, run test:build, destroy the chef server
87
+ ```
88
+
89
+ Last step: add `.chef-workflow` to `.gitignore`. You can change this, but
90
+ until you've done that, it's going to write things to this directory.
91
+
92
+ If you want to do a full test run at this point (which with no tests will do
93
+ nothing but build a chef server and tear it down), feel free to:
94
+
95
+ $ bundle exec test:vagrant:full
96
+
97
+ ## Notes on dependencies
98
+
99
+ As of this writing, the workflow has some pretty strict requirements that we
100
+ hope to make more flexible in the near future. Until then, you should be aware
101
+ of a few things:
102
+
103
+ * Chef 10.16.2 is required. This isn't actually necessary as mentioned above,
104
+ and will be resolved as soon as I can find time to test with earlier
105
+ versions. This has some implications:
106
+
107
+ * Tools like `berkshelf` and `librarian` and `foodcritic` (all add-ins to
108
+ the default workflow) have hard dependencies on earlier versions of chef.
109
+ The tasks that integrate these take this into account, but **you must
110
+ install the gems separately and manually to use them**.
111
+
112
+ * Ruby 1.9 is **required**. We will gladly accept patches to make it 1.8.7
113
+ compatible, but 1.8.7 compatibility is not something we will be actively
114
+ pursuing at this point.
115
+
116
+ ## Usage
117
+
118
+ Everything in this workflow is managed through usage of `rake` tasks, with an
119
+ emphasis on cherry-picking tasks with `chef_workflow_task` into your `Rakefile` and
120
+ configuring them with support configurators like `configure_knife` and
121
+ `configure_vagrant`.
122
+
123
+ The next few sections will briefly cover the high-level design of the system.
124
+ For details, or information on writing your own tasks, hit the
125
+ [wiki](https://github.com/chef-workflow/chef-workflow-tasklib/wiki).
126
+
127
+ For the basic workflow, note that everything is state tracked between runs for
128
+ the most part, so if you build a chef server with `chef_server:create`,
129
+ other tasks will just do the right thing and operate on that chef server. This
130
+ makes it easy to maintain a edit, upload, test, evaluate, repeat workflow as
131
+ you're working on changes. Knife configuration, vagrant "prisons" (See the
132
+ wiki) and allocated IPs are all tracked on exit in the `.chef-workflow`
133
+ directory.
134
+
135
+ There are some environment variables which control various settings, like
136
+ debugging output. The defaults are usually fine, but check out the "Environment
137
+ Variables" section of the
138
+ [chef-workflow](https://github.com/chef-workflow/chef-workflow) `README.md`.
139
+
140
+ ## Picking your own workflow
141
+
142
+ Adding `chef_workflow_task` statements to your workflow is the easiest way to get started.
143
+ We don't expect you to use a resolver, for example, but support both
144
+ [Berkshelf](https://github.com/RiotGames/Berkshelf) and
145
+ [Librarian](https://github.com/applicationsonline/librarian) out of the box.
146
+ Neither of these are required in the default `chef-workflow` require.
147
+
148
+ Many tasks exist in our [tasks
149
+ directory](https://github.com/chef-workflow/chef-workflow-tasklib/tree/master/lib/chef-workflow/tasks)
150
+ and we strongly recommend poking through it if you're interested in fully
151
+ customizing your workflow. Every attempt has been made for each task library to
152
+ pull in only what it needs to operate which allows you to use each independent
153
+ portion without fear of missing essential code.
154
+
155
+ So to add `berkshelf` support, we add this to our Rakefile:
156
+
157
+ ```ruby
158
+ chef_workflow_task 'cookbooks/resolve/berkshelf'
159
+ ```
160
+
161
+ (If you are using berkshelf 0.4.x or earlier, `chef_workflow_task
162
+ 'cookbooks/resolve/berkshelf0.4'`)
163
+
164
+ Which will add a few tasks, `cookbooks:resolve` and `cookbooks:update` and a
165
+ few dependencies. **Note:** due to the way many of these tools declare
166
+ dependencies, they must be installed independently of the bundle with `gem
167
+ install`, so in this case, `gem install berkshelf`. This is out of our control.
168
+
169
+ Let's build a custom workflow. For example let's say we just want to add:
170
+
171
+ * resolving cookbooks with librarian
172
+ * uploading cookbooks
173
+ * uploading roles
174
+ * uploading environments
175
+ * uploading data bags
176
+ * a task that does all of these when we type `bundle exec rake`
177
+
178
+ *You'll have to point this at your live knife configuration* (see the next
179
+ section), but your `Rakefile` would at first look something like this:
180
+
181
+ ```ruby
182
+ chef_workflow_task 'cookbooks/resolve/librarian'
183
+ chef_workflow_task 'cookbooks/upload'
184
+ chef_workflow_task 'chef/roles'
185
+ chef_workflow_task 'chef/environments'
186
+ chef_workflow_task 'chef/data_bags'
187
+
188
+ task :default => %w[
189
+ cookbooks:resolve_and_upload
190
+ chef:roles:upload
191
+ chef:environments:upload
192
+ chef:data_bags:upload
193
+ ]
194
+ ```
195
+
196
+ Adding new rake tasks (or even full task libs) is easy too with the extensible
197
+ configuration system and scaffolding already in place, and utility libraries to
198
+ take the drama out of calling knife plugins or working with collections of
199
+ machines. Please see the
200
+ [wiki](https://github.com/chef-workflow/chef-workflow-tasklib/wiki) for more
201
+ information.
202
+
203
+ ## Configuring the workflow
204
+
205
+ chef-workflow provides you with a number of pre-baked tasks, but say you need
206
+ just one little tweak so you can get with your life. Maybe it's where the
207
+ `.chef-workflow` directory lives or where to work with your cookbooks or what
208
+ vagrant box to use, or whatever. You shouldn't have to rewrite the entire task
209
+ to change that.
210
+
211
+ The `configure_knife` and `configure_vagrant` commands have tooling to assist
212
+ you with this. If you ran the `chef-workflow-bootstrap` tool, you should have a
213
+ file called `lib/chef-workflow-config.rb` which is used to store configuration
214
+ in a central place between this and our testing system.
215
+
216
+ Code like this goes in this file:
217
+
218
+ ```ruby
219
+ configure_vagrant do
220
+ # Use this `box_url` for all vagrant machines.
221
+ box_url "http://files.vagrantup.com/precise64.box"
222
+ end
223
+
224
+ configure_knife do
225
+ roles_path "our-roles" # set the roles directory for chef:roles:upload
226
+ end
227
+ ```
228
+
229
+ For our custom workflow example above, you can twiddle a few bits with
230
+ `configure_knife` to point at known chef configuration locations, which can use
231
+ `~/.chef/knife.rb`, for example. You will want to be careful doing this with
232
+ test integration.
233
+
234
+ `bundle exec rake chef:show_config` can show you most of the settings in a
235
+ system and how you've configured them.
236
+
237
+ Please see the
238
+ [wiki](https://github.com/chef-workflow/chef-workflow-tasklib/wiki) for more
239
+ information on how to manipulate this for your own tasks.
240
+
241
+ ## What's next?
242
+
243
+ * Guard support for change-triggered test runs.
244
+ * Feedback that's more reactive than "everything" or "nothing". The speed (or
245
+ lack thereof) of running large suites makes this especially tricky.
246
+ * See the Issues list for more.
247
+
248
+ ## Problems
249
+
250
+ * It's not fast. EC2 support is faster than Vagrant for most complex cases,
251
+ but it's still pretty slow.
252
+ * It has two effective noise levels: "a lot" and "silent".
253
+
254
+ ## Contributing
255
+
256
+ 1. Fork it
257
+ 2. Create your feature branch (`git checkout -b my-new-feature`)
258
+ 3. Commit your changes (`git commit -am 'Add some feature'`)
259
+ 4. Push to the branch (`git push origin my-new-feature`)
260
+ 5. Create new Pull Request
data/Rakefile ADDED
@@ -0,0 +1 @@
1
+ require "bundler/gem_tasks"
@@ -0,0 +1,25 @@
1
+ # -*- encoding: utf-8 -*-
2
+ lib = File.expand_path('../lib', __FILE__)
3
+ $LOAD_PATH.unshift(lib) unless $LOAD_PATH.include?(lib)
4
+ require 'chef-workflow-tasklib/version'
5
+
6
+ Gem::Specification.new do |gem|
7
+ gem.name = "chef-workflow-tasklib"
8
+ gem.version = Chef::Workflow::Tasklib::VERSION
9
+ gem.authors = ["Erik Hollensbe"]
10
+ gem.email = ["erik+github@hollensbe.org"]
11
+ gem.description = %q{A set of rake tasks provided as discrete libraries for forming a chef workflow}
12
+ gem.summary = %q{A set of rake tasks provided as discrete libraries for forming a chef workflow}
13
+ gem.homepage = "https://github.com/chef-workflow/chef-workflow-tasklib"
14
+
15
+ gem.files = `git ls-files`.split($/)
16
+ gem.executables = gem.files.grep(%r{^bin/}).map{ |f| File.basename(f) }
17
+ gem.test_files = gem.files.grep(%r{^(test|spec|features)/})
18
+ gem.require_paths = ["lib"]
19
+
20
+ gem.add_dependency 'chef-workflow'
21
+ gem.add_dependency 'knife-dsl', '~> 0.1.0'
22
+ gem.add_dependency 'vagrant-dsl', '~> 0.1.0'
23
+ gem.add_dependency 'rake', '~> 0.9'
24
+ gem.add_dependency 'knife-server' '~> 0.3.2'
25
+ end
@@ -0,0 +1,21 @@
1
+ require 'chef-workflow'
2
+
3
+ class Chef
4
+ module Workflow
5
+ module TaskHelper
6
+ def chef_workflow_task(obj)
7
+ require "chef-workflow/tasks/#{obj}"
8
+ end
9
+ end
10
+ end
11
+ end
12
+
13
+ class << eval("self", TOPLEVEL_BINDING)
14
+ include Chef::Workflow::TaskHelper
15
+ end
16
+
17
+ if defined? Rake::DSL
18
+ module Rake::DSL
19
+ include Chef::Workflow::TaskHelper
20
+ end
21
+ end
@@ -0,0 +1,7 @@
1
+ class Chef
2
+ module Workflow
3
+ module Tasklib
4
+ VERSION = "0.1.0"
5
+ end
6
+ end
7
+ end
@@ -0,0 +1,8 @@
1
+ require 'chef-workflow/support/knife'
2
+
3
+ namespace :bootstrap do
4
+ task :knife do
5
+ # this is what knife-dsl needs to know what config to use
6
+ ENV["CHEF_CONFIG"] ||= KnifeSupport.singleton.knife_config_path
7
+ end
8
+ end
@@ -0,0 +1,42 @@
1
+ require 'chef-workflow/support/general'
2
+ require 'chef-workflow/support/ip'
3
+ require 'chef-workflow/support/vagrant'
4
+ require 'chef-workflow/support/ec2'
5
+ require 'chef-workflow/support/knife'
6
+ require 'chef-workflow/support/scheduler'
7
+ require 'chef/config'
8
+ require 'fileutils'
9
+
10
+ namespace :chef do
11
+ namespace :clean do
12
+ desc "Clean up the ip registry for chef-workflow"
13
+ task :ips do
14
+ IPSupport.singleton.reset
15
+ IPSupport.singleton.write
16
+ end
17
+
18
+ desc "Clean up the temporary chef configuration for chef-workflow"
19
+ task :knife do
20
+ FileUtils.rm_rf(KnifeSupport.singleton.chef_config_path)
21
+ FileUtils.rm_f(KnifeSupport.singleton.knife_config_path)
22
+ end
23
+
24
+ desc "Clean up the machines that a previous chef-workflow run generated"
25
+ task :machines do
26
+ if File.exist?(KnifeSupport.singleton.knife_config_path)
27
+ Chef::Config.from_file(KnifeSupport.singleton.knife_config_path)
28
+ s = Scheduler.new(false)
29
+ s.serial = true
30
+ s.force_deprovision = true
31
+ s.teardown(%w[chef-server])
32
+ s.write_state
33
+ end
34
+ end
35
+ end
36
+
37
+ desc "Clean up the entire chef-workflow directory and machines"
38
+ task :clean => [ "chef:clean:machines", "chef_server:destroy" ] do
39
+ EC2Support.singleton.destroy_security_group
40
+ FileUtils.rm_rf(GeneralSupport.singleton.workflow_dir)
41
+ end
42
+ end
@@ -0,0 +1,37 @@
1
+ require 'knife/dsl'
2
+ require 'chef-workflow/tasks/bootstrap/knife'
3
+
4
+ namespace :chef do
5
+ namespace :data_bags do
6
+ desc "Upload your data bags to the chef server"
7
+ task :upload => [ "bootstrap:knife" ] do
8
+ if File.directory?(KnifeSupport.singleton.data_bags_path)
9
+ # bag names: basename of data_bags/*. This presumes your data bags path
10
+ # is structured like so:
11
+ #
12
+ # data_bags/my_bag # bag name
13
+ # data_bags/my_bag/my_item.(rb|json) # bag item
14
+ #
15
+ # note that while it makes an attempt to select by filename vs.
16
+ # directory in the right spots. will probably blow up spectacularly
17
+ # explode if you deviate heavily from this directory structure.
18
+ #
19
+ bag_names = Dir[File.join(KnifeSupport.singleton.data_bags_path, "*")].
20
+ select { |x| File.directory?(x) }.
21
+ map { |x| File.basename(x) }
22
+
23
+ bag_names.each do |bag|
24
+ status = knife %W[data bag create #{bag}]
25
+ # XXX this doesn't fail if the data bag already exists.
26
+ # we're actually depending on this.
27
+ fail if status != 0
28
+
29
+ bag_items = Dir[File.join(KnifeSupport.singleton.data_bags_path, bag, '*')].
30
+ select { |x| !File.directory?(x) }
31
+ status = knife %W[data bag from file #{bag}] + bag_items
32
+ fail if status != 0
33
+ end
34
+ end
35
+ end
36
+ end
37
+ end
@@ -0,0 +1,14 @@
1
+ require 'knife/dsl'
2
+ require 'chef-workflow/tasks/bootstrap/knife'
3
+
4
+ namespace :chef do
5
+ namespace :environments do
6
+ desc "Upload your environments to the chef server"
7
+ task :upload => [ "bootstrap:knife" ] do
8
+ if File.directory?(KnifeSupport.singleton.environments_path)
9
+ status = knife %W[environment from file] + Dir[File.join(KnifeSupport.singleton.environments_path, '*')]
10
+ fail if status != 0
11
+ end
12
+ end
13
+ end
14
+ end
@@ -0,0 +1,14 @@
1
+ require 'knife/dsl'
2
+ require 'chef-workflow/tasks/bootstrap/knife'
3
+
4
+ namespace :chef do
5
+ namespace :roles do
6
+ desc "Upload your roles to the chef server"
7
+ task :upload => [ "bootstrap:knife" ] do
8
+ if File.directory?(KnifeSupport.singleton.roles_path)
9
+ status = knife %W[role from file] + Dir[File.join(KnifeSupport.singleton.roles_path, '*')]
10
+ fail if status != 0
11
+ end
12
+ end
13
+ end
14
+ end
@@ -0,0 +1,38 @@
1
+ require 'chef-workflow/support/general'
2
+ require 'chef-workflow/support/ip'
3
+ require 'chef-workflow/support/knife'
4
+ require 'chef-workflow/support/vagrant'
5
+
6
+ namespace :chef do
7
+ desc "Show the calculated configuration for chef-workflow"
8
+ task :show_config do
9
+ puts "general:"
10
+ puts "\tworkflow_dir: #{GeneralSupport.singleton.workflow_dir}"
11
+ puts "\tvm_file: #{GeneralSupport.singleton.vm_file}"
12
+ puts "\tchef_server_prison: #{GeneralSupport.singleton.chef_server_prison}"
13
+ puts "\tmachine_provisoner: #{GeneralSupport.singleton.machine_provisioner}"
14
+
15
+ puts "knife:"
16
+ mute = %w[knife_config_template]
17
+ KnifeSupport::DEFAULTS.keys.reject { |x| mute.include?(x.to_s) }.each do |key|
18
+ puts "\t#{key}: #{KnifeSupport.singleton.send(key)}"
19
+ end
20
+
21
+ puts "vagrant:"
22
+ puts "\tip subnet (/24): #{IPSupport.singleton.subnet}"
23
+ puts "\tbox url: #{VagrantSupport.singleton.box_url}"
24
+
25
+ puts "ec2:"
26
+
27
+ %w[
28
+ ami
29
+ instance_type
30
+ region
31
+ ssh_key
32
+ security_groups
33
+ security_group_open_ports
34
+ ].each do |key|
35
+ puts "\t#{key}: #{EC2Support.singleton.send(key)}"
36
+ end
37
+ end
38
+ end
@@ -0,0 +1,14 @@
1
+ chef_workflow_task 'chef/data_bags'
2
+ chef_workflow_task 'chef/environments'
3
+ chef_workflow_task 'chef/roles'
4
+ chef_workflow_task 'cookbooks/upload'
5
+
6
+ namespace :chef do
7
+ desc "Upload everything."
8
+ task :upload => %w[
9
+ cookbooks:upload
10
+ chef:roles:upload
11
+ chef:environments:upload
12
+ chef:data_bags:upload
13
+ ]
14
+ end
@@ -0,0 +1,41 @@
1
+ require 'chef-workflow/support/general'
2
+ require 'chef-workflow/support/knife'
3
+ require 'chef-workflow/support/scheduler'
4
+
5
+ namespace :chef_server do
6
+ desc "Create a chef server with the #{GeneralSupport.singleton.machine_provisioner} provisioner"
7
+ task :create do
8
+ # FIXME not really happy with having to repeat this at the end, but it's
9
+ # necessary. maybe a subroutine in the right place in the future is the
10
+ # best approach, but I'm feeling lazy right now.
11
+ KnifeSupport.singleton.build_knife_config
12
+ Chef::Config.from_file(KnifeSupport.singleton.knife_config_path)
13
+
14
+ s = Scheduler.new(false)
15
+ s.serial = true
16
+
17
+ s.schedule_provision(
18
+ 'chef-server',
19
+ [
20
+ GeneralSupport.singleton.machine_provisioner.new('chef-server', 1),
21
+ VM::ChefServerProvisioner.new
22
+ ],
23
+ []
24
+ )
25
+
26
+ s.run
27
+ s.wait_for('chef-server') # probably superfluous
28
+ s.write_state
29
+
30
+ KnifeSupport.singleton.build_knife_config
31
+ Chef::Config.from_file(KnifeSupport.singleton.knife_config_path)
32
+ end
33
+
34
+ desc "Destroy the chef server"
35
+ task :destroy do
36
+ s = Scheduler.new(false)
37
+ s.serial = true
38
+ s.force_deprovision = true
39
+ s.teardown_group('chef-server')
40
+ end
41
+ end
@@ -0,0 +1,16 @@
1
+ require 'chef-workflow/support/knife'
2
+
3
+ KnifeSupport.add_attribute :fc_cookbooks_path, File.join(Dir.pwd, 'cookbooks')
4
+ KnifeSupport.add_attribute :fc_options, [ ]
5
+
6
+ namespace :cookbooks do
7
+ desc "Run the cookbooks through foodcritic"
8
+ task :foodcritic do
9
+ Rake::Task["cookbooks:resolve"].invoke rescue nil
10
+ if File.directory?(KnifeSupport.singleton.fc_cookbooks_path)
11
+ Bundler.with_clean_env do
12
+ sh "foodcritic #{KnifeSupport.singleton.fc_cookbooks_path} #{KnifeSupport.singleton.fc_options.join(" ")}"
13
+ end
14
+ end
15
+ end
16
+ end
@@ -0,0 +1,2 @@
1
+ $BERKSHELF_ARG = "path"
2
+ load File.join(File.dirname(__FILE__), 'berkshelf/berkshelf-base.rb')
@@ -0,0 +1,21 @@
1
+ load File.join(File.dirname(__FILE__), '../bootstrap.rb')
2
+
3
+ # Both berkshelf and librarian have ... aggressive dependencies. They usually are
4
+ # a great way to break your Gemfile if you have chef in it.
5
+ namespace :cookbooks do
6
+ desc "Resolve cookbooks and populate using Berkshelf"
7
+ task :resolve => [ "bootstrap:knife" ] do
8
+ if File.directory?(KnifeSupport.singleton.cookbooks_path)
9
+ Bundler.with_clean_env do
10
+ sh "berks install --#{$BERKSHELF_ARG} #{KnifeSupport.singleton.cookbooks_path}"
11
+ end
12
+ end
13
+ end
14
+
15
+ desc "Update your locked cookbooks with Berkshelf"
16
+ task :update => [ "bootstrap:knife" ] do
17
+ Bundler.with_clean_env do
18
+ sh "berks update"
19
+ end
20
+ end
21
+ end
@@ -0,0 +1,3 @@
1
+ $BERKSHELF_ARG = "shims"
2
+
3
+ load File.join(File.dirname(__FILE__), 'berkshelf/berkshelf-base.rb')
@@ -0,0 +1,10 @@
1
+ # used by resolver tasklibs to ensure their basic dependencies are met. Not to
2
+ # be used directly.
3
+ begin
4
+ Rake::Task["cookbooks:resolve"].clear
5
+ Rake::Task["cookbooks:update"].clear
6
+ rescue
7
+ end
8
+
9
+ require 'chef-workflow/tasks/bootstrap/knife'
10
+ require 'chef-workflow/tasks/cookbooks/resolve_and_upload'
@@ -0,0 +1,21 @@
1
+ load File.join(File.dirname(__FILE__), 'bootstrap.rb')
2
+
3
+ # Both berkshelf and librarian have ... aggressive dependencies. They usually are
4
+ # a great way to break your Gemfile if you have chef in it.
5
+ namespace :cookbooks do
6
+ desc "Resolve cookbooks and populate using Librarian"
7
+ task :resolve => [ "bootstrap:knife" ] do
8
+ if File.directory?(KnifeSupport.singleton.cookbooks_path)
9
+ Bundler.with_clean_env do
10
+ sh "librarian-chef install --path #{KnifeSupport.singleton.cookbooks_path}"
11
+ end
12
+ end
13
+ end
14
+
15
+ desc "Update your locked cookbooks with Librarian"
16
+ task :update => [ "bootstrap:knife" ] do
17
+ Bundler.with_clean_env do
18
+ sh "librarian-chef update"
19
+ end
20
+ end
21
+ end
@@ -0,0 +1,6 @@
1
+ require 'chef-workflow/tasks/cookbooks/upload'
2
+
3
+ namespace :cookbooks do
4
+ desc "Run the cookbook resolver and upload the result to the chef server."
5
+ task :resolve_and_upload => [ "cookbooks:resolve", "cookbooks:upload" ]
6
+ end
@@ -0,0 +1,10 @@
1
+ require 'knife/dsl'
2
+ require 'chef-workflow/tasks/bootstrap/knife'
3
+
4
+ namespace :cookbooks do
5
+ desc "Upload your cookbooks to the chef server"
6
+ task :upload => [ "bootstrap:knife" ] do
7
+ result = knife %W[cookbook upload -a]
8
+ fail if result != 0
9
+ end
10
+ end
@@ -0,0 +1,6 @@
1
+ chef_workflow_task 'chef_server'
2
+ chef_workflow_task 'cookbooks/upload'
3
+ chef_workflow_task 'chef/upload'
4
+ chef_workflow_task 'chef/show_config'
5
+ chef_workflow_task 'chef/clean'
6
+ chef_workflow_task 'test/build'
@@ -0,0 +1,69 @@
1
+ require 'rake/testtask'
2
+ require 'chef-workflow/support/scheduler'
3
+ require 'chef-workflow/support/knife'
4
+
5
+ Rake::TestTask.new do |t|
6
+ t.libs << "test"
7
+ t.test_files = Dir["test/**/test_*.rb"]
8
+ t.verbose = true
9
+ end
10
+
11
+ namespace :test do
12
+ desc "Test recipes in the test_recipes configuration."
13
+
14
+ task :recipes => [ "recipes:cleanup" ] do
15
+ Chef::Config.from_file(KnifeSupport.singleton.knife_config_path)
16
+
17
+ s = Scheduler.new(true)
18
+ s.run
19
+
20
+ groups =
21
+ KnifeSupport.singleton.test_recipes.map do |recipe|
22
+ group_name = "recipe-#{recipe.gsub(/::/, '-')}"
23
+
24
+ kp = VM::KnifeProvisioner.new
25
+ kp.username = KnifeSupport.singleton.ssh_user
26
+ kp.password = KnifeSupport.singleton.ssh_password
27
+ kp.use_sudo = KnifeSupport.singleton.use_sudo
28
+ kp.ssh_key = KnifeSupport.singleton.ssh_identity_file
29
+ kp.environment = KnifeSupport.singleton.test_environment
30
+ kp.run_list = [ "recipe[#{recipe}]", "recipe[minitest-handler]" ]
31
+ kp.solr_check = false
32
+
33
+ s.schedule_provision(
34
+ group_name,
35
+ [
36
+ GeneralSupport.singleton.machine_provisioner.new(group_name, 1),
37
+ kp
38
+ ]
39
+ )
40
+
41
+ group_name
42
+ end
43
+
44
+ s.wait_for(*groups)
45
+
46
+ groups.each do |group_name|
47
+ s.teardown_group(group_name)
48
+ end
49
+
50
+ s.write_state
51
+ end
52
+
53
+ namespace :recipes do
54
+ desc "Cleanup any stale instances created running recipe tests."
55
+ task :cleanup do
56
+ Chef::Config.from_file(KnifeSupport.singleton.knife_config_path)
57
+ s = Scheduler.new(false)
58
+ s.run
59
+
60
+ s.vm_groups.select do |g, v|
61
+ g.start_with?("recipe-")
62
+ end.each do |g, v|
63
+ s.teardown_group(g, false)
64
+ end
65
+
66
+ s.write_state
67
+ end
68
+ end
69
+ end
@@ -0,0 +1,37 @@
1
+ require 'chef-workflow/tasks/test'
2
+ require 'chef-workflow/tasks/chef/upload'
3
+ require 'chef-workflow/tasks/chef/clean'
4
+
5
+ namespace :test do
6
+ task :resolve_hack do
7
+ begin
8
+ Rake::Task["cookbooks:resolve"].invoke
9
+ rescue
10
+ end
11
+ end
12
+
13
+ desc "Refresh all global meta on the chef server"
14
+ task :refresh => [
15
+ "test:resolve_hack",
16
+ "chef:upload"
17
+ ]
18
+
19
+ desc "test:refresh and test"
20
+ task :build => [
21
+ "test:refresh",
22
+ "test"
23
+ ]
24
+
25
+ desc "chef:clean:machines and test:build"
26
+ task :rebuild => [
27
+ "chef:clean:machines",
28
+ "test:build"
29
+ ]
30
+
31
+ desc "Build a chef server, run test:build, destroy the chef server"
32
+ task :full => [
33
+ "chef_server:create",
34
+ "test:build",
35
+ "chef:clean"
36
+ ]
37
+ end
metadata ADDED
@@ -0,0 +1,154 @@
1
+ --- !ruby/object:Gem::Specification
2
+ name: chef-workflow-tasklib
3
+ version: !ruby/object:Gem::Version
4
+ version: 0.1.0
5
+ prerelease:
6
+ platform: ruby
7
+ authors:
8
+ - Erik Hollensbe
9
+ autorequire:
10
+ bindir: bin
11
+ cert_chain: []
12
+ date: 2012-12-21 00:00:00.000000000 Z
13
+ dependencies:
14
+ - !ruby/object:Gem::Dependency
15
+ name: chef-workflow
16
+ requirement: !ruby/object:Gem::Requirement
17
+ none: false
18
+ requirements:
19
+ - - ! '>='
20
+ - !ruby/object:Gem::Version
21
+ version: '0'
22
+ type: :runtime
23
+ prerelease: false
24
+ version_requirements: !ruby/object:Gem::Requirement
25
+ none: false
26
+ requirements:
27
+ - - ! '>='
28
+ - !ruby/object:Gem::Version
29
+ version: '0'
30
+ - !ruby/object:Gem::Dependency
31
+ name: knife-dsl
32
+ requirement: !ruby/object:Gem::Requirement
33
+ none: false
34
+ requirements:
35
+ - - ~>
36
+ - !ruby/object:Gem::Version
37
+ version: 0.1.0
38
+ type: :runtime
39
+ prerelease: false
40
+ version_requirements: !ruby/object:Gem::Requirement
41
+ none: false
42
+ requirements:
43
+ - - ~>
44
+ - !ruby/object:Gem::Version
45
+ version: 0.1.0
46
+ - !ruby/object:Gem::Dependency
47
+ name: vagrant-dsl
48
+ requirement: !ruby/object:Gem::Requirement
49
+ none: false
50
+ requirements:
51
+ - - ~>
52
+ - !ruby/object:Gem::Version
53
+ version: 0.1.0
54
+ type: :runtime
55
+ prerelease: false
56
+ version_requirements: !ruby/object:Gem::Requirement
57
+ none: false
58
+ requirements:
59
+ - - ~>
60
+ - !ruby/object:Gem::Version
61
+ version: 0.1.0
62
+ - !ruby/object:Gem::Dependency
63
+ name: rake
64
+ requirement: !ruby/object:Gem::Requirement
65
+ none: false
66
+ requirements:
67
+ - - ~>
68
+ - !ruby/object:Gem::Version
69
+ version: '0.9'
70
+ type: :runtime
71
+ prerelease: false
72
+ version_requirements: !ruby/object:Gem::Requirement
73
+ none: false
74
+ requirements:
75
+ - - ~>
76
+ - !ruby/object:Gem::Version
77
+ version: '0.9'
78
+ - !ruby/object:Gem::Dependency
79
+ name: knife-server~> 0.3.2
80
+ requirement: !ruby/object:Gem::Requirement
81
+ none: false
82
+ requirements:
83
+ - - ! '>='
84
+ - !ruby/object:Gem::Version
85
+ version: '0'
86
+ type: :runtime
87
+ prerelease: false
88
+ version_requirements: !ruby/object:Gem::Requirement
89
+ none: false
90
+ requirements:
91
+ - - ! '>='
92
+ - !ruby/object:Gem::Version
93
+ version: '0'
94
+ description: A set of rake tasks provided as discrete libraries for forming a chef
95
+ workflow
96
+ email:
97
+ - erik+github@hollensbe.org
98
+ executables: []
99
+ extensions: []
100
+ extra_rdoc_files: []
101
+ files:
102
+ - .gitignore
103
+ - Gemfile
104
+ - LICENSE.txt
105
+ - README.md
106
+ - Rakefile
107
+ - chef-workflow-tasklib.gemspec
108
+ - lib/chef-workflow-tasklib.rb
109
+ - lib/chef-workflow-tasklib/version.rb
110
+ - lib/chef-workflow/tasks/bootstrap/knife.rb
111
+ - lib/chef-workflow/tasks/chef/clean.rb
112
+ - lib/chef-workflow/tasks/chef/data_bags.rb
113
+ - lib/chef-workflow/tasks/chef/environments.rb
114
+ - lib/chef-workflow/tasks/chef/roles.rb
115
+ - lib/chef-workflow/tasks/chef/show_config.rb
116
+ - lib/chef-workflow/tasks/chef/upload.rb
117
+ - lib/chef-workflow/tasks/chef_server.rb
118
+ - lib/chef-workflow/tasks/cookbooks/foodcritic.rb
119
+ - lib/chef-workflow/tasks/cookbooks/resolve/berkshelf.rb
120
+ - lib/chef-workflow/tasks/cookbooks/resolve/berkshelf/berkshelf-base.rb
121
+ - lib/chef-workflow/tasks/cookbooks/resolve/berkshelf0.4.rb
122
+ - lib/chef-workflow/tasks/cookbooks/resolve/bootstrap.rb
123
+ - lib/chef-workflow/tasks/cookbooks/resolve/librarian.rb
124
+ - lib/chef-workflow/tasks/cookbooks/resolve_and_upload.rb
125
+ - lib/chef-workflow/tasks/cookbooks/upload.rb
126
+ - lib/chef-workflow/tasks/default.rb
127
+ - lib/chef-workflow/tasks/test.rb
128
+ - lib/chef-workflow/tasks/test/build.rb
129
+ homepage: https://github.com/chef-workflow/chef-workflow-tasklib
130
+ licenses: []
131
+ post_install_message:
132
+ rdoc_options: []
133
+ require_paths:
134
+ - lib
135
+ required_ruby_version: !ruby/object:Gem::Requirement
136
+ none: false
137
+ requirements:
138
+ - - ! '>='
139
+ - !ruby/object:Gem::Version
140
+ version: '0'
141
+ required_rubygems_version: !ruby/object:Gem::Requirement
142
+ none: false
143
+ requirements:
144
+ - - ! '>='
145
+ - !ruby/object:Gem::Version
146
+ version: '0'
147
+ requirements: []
148
+ rubyforge_project:
149
+ rubygems_version: 1.8.24
150
+ signing_key:
151
+ specification_version: 3
152
+ summary: A set of rake tasks provided as discrete libraries for forming a chef workflow
153
+ test_files: []
154
+ has_rdoc: