cucumber-chef 0.4.0
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.
- data/.document +5 -0
- data/.gitignore +45 -0
- data/Gemfile +21 -0
- data/LICENSE +201 -0
- data/README.md +83 -0
- data/Rakefile +53 -0
- data/VERSION +1 -0
- data/bin/cucumber-chef +162 -0
- data/cookbooks/cucumber-chef/README.rdoc +8 -0
- data/cookbooks/cucumber-chef/files/default/add-git-identity +2 -0
- data/cookbooks/cucumber-chef/files/default/controller-first-boot +1 -0
- data/cookbooks/cucumber-chef/files/default/cucumber-net +5 -0
- data/cookbooks/cucumber-chef/files/default/cucumber-private-key +27 -0
- data/cookbooks/cucumber-chef/files/default/cucumber-run_list +1 -0
- data/cookbooks/cucumber-chef/files/default/git-private-key +27 -0
- data/cookbooks/cucumber-chef/files/default/install-chef +1 -0
- data/cookbooks/cucumber-chef/files/default/lxc-controller-network-config +5 -0
- data/cookbooks/cucumber-chef/files/default/lxc-lucid-chef +377 -0
- data/cookbooks/cucumber-chef/files/default/permissive-ssh-config +3 -0
- data/cookbooks/cucumber-chef/metadata.rb +6 -0
- data/cookbooks/cucumber-chef/recipes/controller.rb +50 -0
- data/cookbooks/cucumber-chef/recipes/lxc.rb +35 -0
- data/cookbooks/cucumber-chef/recipes/test_lab.rb +23 -0
- data/cookbooks/cucumber-chef/recipes/testrunner.rb +46 -0
- data/cookbooks/cucumber-chef/roles/controller.rb +7 -0
- data/cookbooks/cucumber-chef/roles/test_lab_test.rb +9 -0
- data/cookbooks/cucumber-chef/templates/default/controller-client.erb +5 -0
- data/cookbooks/cucumber-chef/templates/default/lxc-lucid-chef +385 -0
- data/cucumber-chef.gemspec +118 -0
- data/features/installing.feature +10 -0
- data/features/steps/installing_steps.rb +34 -0
- data/features/steps/setup_steps.rb +32 -0
- data/features/steps/upload_steps.rb +11 -0
- data/features/steps/usage_steps.rb +62 -0
- data/features/support/env.rb +25 -0
- data/features/support/filetools.rb +9 -0
- data/features/support/silent_system.rb +4 -0
- data/features/usage.feature +26 -0
- data/lib/cucumber-chef.rb +1 -0
- data/lib/cucumber/chef.rb +195 -0
- data/lib/cucumber/chef/handy.rb +87 -0
- data/lib/cucumber/chef/templates/controller.erb +35 -0
- data/lib/cucumber/chef/templates/env.rb +16 -0
- data/lib/cucumber/chef/templates/example_feature.erb +11 -0
- data/lib/cucumber/chef/templates/example_step.erb +19 -0
- data/lib/cucumber/chef/templates/readme.erb +28 -0
- data/lib/cucumber/chef/templates/ubuntu10.04-gems.erb +43 -0
- data/lib/cucumber/chef/version.rb +5 -0
- data/lib/cucumber/ec2_server_create.rb +99 -0
- data/spec/unit/cucumber_chef_spec.rb +270 -0
- metadata +213 -0
@@ -0,0 +1,118 @@
|
|
1
|
+
# Generated by jeweler
|
2
|
+
# DO NOT EDIT THIS FILE DIRECTLY
|
3
|
+
# Instead, edit Jeweler::Tasks in Rakefile, and run 'rake gemspec'
|
4
|
+
# -*- encoding: utf-8 -*-
|
5
|
+
|
6
|
+
Gem::Specification.new do |s|
|
7
|
+
s.name = %q{cucumber-chef}
|
8
|
+
s.version = "0.4.0"
|
9
|
+
|
10
|
+
s.required_rubygems_version = Gem::Requirement.new(">= 0") if s.respond_to? :required_rubygems_version=
|
11
|
+
s.authors = ["Stephen Nelson-Smith"]
|
12
|
+
s.date = %q{2011-06-06}
|
13
|
+
s.default_executable = %q{cucumber-chef}
|
14
|
+
s.description = %q{Framework for behaviour-drive infrastructure development.}
|
15
|
+
s.email = %q{stephen@atalanta-systems.com}
|
16
|
+
s.executables = ["cucumber-chef"]
|
17
|
+
s.extra_rdoc_files = [
|
18
|
+
"LICENSE",
|
19
|
+
"README.md"
|
20
|
+
]
|
21
|
+
s.files = [
|
22
|
+
".document",
|
23
|
+
".gitignore",
|
24
|
+
"Gemfile",
|
25
|
+
"LICENSE",
|
26
|
+
"README.md",
|
27
|
+
"Rakefile",
|
28
|
+
"VERSION",
|
29
|
+
"bin/cucumber-chef",
|
30
|
+
"cookbooks/cucumber-chef/README.rdoc",
|
31
|
+
"cookbooks/cucumber-chef/files/default/add-git-identity",
|
32
|
+
"cookbooks/cucumber-chef/files/default/controller-first-boot",
|
33
|
+
"cookbooks/cucumber-chef/files/default/cucumber-net",
|
34
|
+
"cookbooks/cucumber-chef/files/default/cucumber-private-key",
|
35
|
+
"cookbooks/cucumber-chef/files/default/cucumber-run_list",
|
36
|
+
"cookbooks/cucumber-chef/files/default/git-private-key",
|
37
|
+
"cookbooks/cucumber-chef/files/default/install-chef",
|
38
|
+
"cookbooks/cucumber-chef/files/default/lxc-controller-network-config",
|
39
|
+
"cookbooks/cucumber-chef/files/default/lxc-lucid-chef",
|
40
|
+
"cookbooks/cucumber-chef/files/default/permissive-ssh-config",
|
41
|
+
"cookbooks/cucumber-chef/metadata.rb",
|
42
|
+
"cookbooks/cucumber-chef/recipes/controller.rb",
|
43
|
+
"cookbooks/cucumber-chef/recipes/lxc.rb",
|
44
|
+
"cookbooks/cucumber-chef/recipes/test_lab.rb",
|
45
|
+
"cookbooks/cucumber-chef/recipes/testrunner.rb",
|
46
|
+
"cookbooks/cucumber-chef/roles/controller.rb",
|
47
|
+
"cookbooks/cucumber-chef/roles/test_lab_test.rb",
|
48
|
+
"cookbooks/cucumber-chef/templates/default/controller-client.erb",
|
49
|
+
"cookbooks/cucumber-chef/templates/default/lxc-lucid-chef",
|
50
|
+
"cucumber-chef.gemspec",
|
51
|
+
"features/installing.feature",
|
52
|
+
"features/steps/installing_steps.rb",
|
53
|
+
"features/steps/setup_steps.rb",
|
54
|
+
"features/steps/upload_steps.rb",
|
55
|
+
"features/steps/usage_steps.rb",
|
56
|
+
"features/support/env.rb",
|
57
|
+
"features/support/filetools.rb",
|
58
|
+
"features/support/silent_system.rb",
|
59
|
+
"features/usage.feature",
|
60
|
+
"lib/cucumber-chef.rb",
|
61
|
+
"lib/cucumber/chef.rb",
|
62
|
+
"lib/cucumber/chef/handy.rb",
|
63
|
+
"lib/cucumber/chef/templates/controller.erb",
|
64
|
+
"lib/cucumber/chef/templates/env.rb",
|
65
|
+
"lib/cucumber/chef/templates/example_feature.erb",
|
66
|
+
"lib/cucumber/chef/templates/example_step.erb",
|
67
|
+
"lib/cucumber/chef/templates/readme.erb",
|
68
|
+
"lib/cucumber/chef/templates/ubuntu10.04-gems.erb",
|
69
|
+
"lib/cucumber/chef/version.rb",
|
70
|
+
"lib/cucumber/ec2_server_create.rb",
|
71
|
+
"spec/unit/cucumber_chef_spec.rb"
|
72
|
+
]
|
73
|
+
s.homepage = %q{http://github.com/atalanta/cucumber-chef}
|
74
|
+
s.licenses = ["MIT"]
|
75
|
+
s.require_paths = ["lib"]
|
76
|
+
s.rubygems_version = %q{1.6.2}
|
77
|
+
s.summary = %q{Tests Chef-built infrastructure}
|
78
|
+
|
79
|
+
if s.respond_to? :specification_version then
|
80
|
+
s.specification_version = 3
|
81
|
+
|
82
|
+
if Gem::Version.new(Gem::VERSION) >= Gem::Version.new('1.2.0') then
|
83
|
+
s.add_runtime_dependency(%q<chef>, [">= 0.10.0"])
|
84
|
+
s.add_runtime_dependency(%q<cucumber>, [">= 0"])
|
85
|
+
s.add_runtime_dependency(%q<cucumber-nagios>, [">= 0"])
|
86
|
+
s.add_runtime_dependency(%q<rspec>, [">= 0"])
|
87
|
+
s.add_runtime_dependency(%q<fog>, [">= 0"])
|
88
|
+
s.add_runtime_dependency(%q<thor>, [">= 0"])
|
89
|
+
s.add_runtime_dependency(%q<awesome_print>, [">= 0"])
|
90
|
+
s.add_development_dependency(%q<bundler>, ["~> 1.0.0"])
|
91
|
+
s.add_development_dependency(%q<jeweler>, ["~> 1.6.2"])
|
92
|
+
s.add_development_dependency(%q<rcov>, [">= 0"])
|
93
|
+
else
|
94
|
+
s.add_dependency(%q<chef>, [">= 0.10.0"])
|
95
|
+
s.add_dependency(%q<cucumber>, [">= 0"])
|
96
|
+
s.add_dependency(%q<cucumber-nagios>, [">= 0"])
|
97
|
+
s.add_dependency(%q<rspec>, [">= 0"])
|
98
|
+
s.add_dependency(%q<fog>, [">= 0"])
|
99
|
+
s.add_dependency(%q<thor>, [">= 0"])
|
100
|
+
s.add_dependency(%q<awesome_print>, [">= 0"])
|
101
|
+
s.add_dependency(%q<bundler>, ["~> 1.0.0"])
|
102
|
+
s.add_dependency(%q<jeweler>, ["~> 1.6.2"])
|
103
|
+
s.add_dependency(%q<rcov>, [">= 0"])
|
104
|
+
end
|
105
|
+
else
|
106
|
+
s.add_dependency(%q<chef>, [">= 0.10.0"])
|
107
|
+
s.add_dependency(%q<cucumber>, [">= 0"])
|
108
|
+
s.add_dependency(%q<cucumber-nagios>, [">= 0"])
|
109
|
+
s.add_dependency(%q<rspec>, [">= 0"])
|
110
|
+
s.add_dependency(%q<fog>, [">= 0"])
|
111
|
+
s.add_dependency(%q<thor>, [">= 0"])
|
112
|
+
s.add_dependency(%q<awesome_print>, [">= 0"])
|
113
|
+
s.add_dependency(%q<bundler>, ["~> 1.0.0"])
|
114
|
+
s.add_dependency(%q<jeweler>, ["~> 1.6.2"])
|
115
|
+
s.add_dependency(%q<rcov>, [">= 0"])
|
116
|
+
end
|
117
|
+
end
|
118
|
+
|
@@ -0,0 +1,10 @@
|
|
1
|
+
Feature: Installation
|
2
|
+
So that I can run cucumber-chef to test my Chef recipes
|
3
|
+
As a user
|
4
|
+
I can install the gem
|
5
|
+
|
6
|
+
Scenario: Installing the gem
|
7
|
+
When I build the gem
|
8
|
+
And I install the latest gem
|
9
|
+
Then I should have cucumber-chef on my path
|
10
|
+
And I can get help about the cucumber-chef binary on the command line
|
@@ -0,0 +1,34 @@
|
|
1
|
+
When /^I build the gem$/ do
|
2
|
+
project_root = Pathname.new(File.dirname(__FILE__)).parent.parent.expand_path
|
3
|
+
rakefile = File.join(project_root, 'Rakefile')
|
4
|
+
File.exist?(rakefile).should be_true
|
5
|
+
|
6
|
+
# For some unknown reason, the following fails with
|
7
|
+
# Don't know how to build task 'default'
|
8
|
+
# Even though running the below in irb, and rake -f Rakefile build
|
9
|
+
# works fine
|
10
|
+
#
|
11
|
+
# silent_system('rake -f #{rakefile} build').should be_true
|
12
|
+
|
13
|
+
# HACK: using no path for now
|
14
|
+
|
15
|
+
silent_system('rake build').should be_true
|
16
|
+
|
17
|
+
end
|
18
|
+
|
19
|
+
When /^I install the latest gem$/ do
|
20
|
+
project_root = Pathname.new(File.dirname(__FILE__)).parent.parent.expand_path
|
21
|
+
pkg_dir = project_root.join('pkg')
|
22
|
+
glob = File.join(pkg_dir, '*.gem')
|
23
|
+
latest = Dir.glob(glob).sort {|a, b| File.ctime(a) <=> File.ctime(b) }.last
|
24
|
+
silent_system("gem install #{latest} --no-ri --no-rdoc").should be_true
|
25
|
+
end
|
26
|
+
|
27
|
+
Then /^I should have cucumber\-chef on my path$/ do
|
28
|
+
silent_system("which cucumber-chef").should be_true
|
29
|
+
end
|
30
|
+
|
31
|
+
Then /^I can get help about the cucumber\-chef binary on the command line$/ do
|
32
|
+
help_text = %x[cucumber-chef help]
|
33
|
+
help_text.include?("cucumber-chef help [TASK]").should be_true
|
34
|
+
end
|
@@ -0,0 +1,32 @@
|
|
1
|
+
require 'rubygems'
|
2
|
+
require 'fog'
|
3
|
+
|
4
|
+
Given /^I have an Opscode Platform account$/ do
|
5
|
+
silent_system("cucumber-chef genconfig")
|
6
|
+
file_should_exist( "~/.cucumber-chef-sample" )
|
7
|
+
config = YAML::load( File.open( File.expand_path('~/.cucumber-chef-sample') ) )
|
8
|
+
username = config['chef_node_name']
|
9
|
+
req = Net::HTTP.new('community.opscode.com', 80)
|
10
|
+
req.request_head("/users/#{username}").code.should == "200"
|
11
|
+
end
|
12
|
+
|
13
|
+
Given /^an EC2 account$/ do
|
14
|
+
config = YAML::load( File.open( File.expand_path('~/.cucumber-chef-sample') ) )
|
15
|
+
access_key = config["aws_access_key"]
|
16
|
+
secret_key = config["aws_secret_key"]
|
17
|
+
compute = Fog::Compute.new(:provider => 'AWS', :aws_access_key_id => access_key, :aws_secret_access_key => secret_key)
|
18
|
+
compute.describe_availability_zones.should_not be_nil
|
19
|
+
end
|
20
|
+
|
21
|
+
Given /^I have chef installed on my machine$/ do
|
22
|
+
silent_system("which chef-client").should be_true
|
23
|
+
end
|
24
|
+
|
25
|
+
When /^I run cucumber\-chef setup$/ do
|
26
|
+
@output = %x[cucumber-chef setup --config=#{File.expand_path('~/.cucumber-chef-sample')}]
|
27
|
+
end
|
28
|
+
|
29
|
+
Then /^I should be told the instance id and IP address$/ do
|
30
|
+
@output.should match(/i-[0-9a-f]{8}/)
|
31
|
+
@instance_ip_address = @output[/IP Address ([\d|\.]+)/, 1]
|
32
|
+
end
|
@@ -0,0 +1,11 @@
|
|
1
|
+
Given /^I have a cucumber\-chef project$/ do
|
2
|
+
pending # express the regexp above with the code you wish you had
|
3
|
+
end
|
4
|
+
|
5
|
+
When /^I run cucumber\-chef upload$/ do
|
6
|
+
pending # express the regexp above with the code you wish you had
|
7
|
+
end
|
8
|
+
|
9
|
+
Then /^my tests should be available on the test lab$/ do
|
10
|
+
pending # express the regexp above with the code you wish you had
|
11
|
+
end
|
@@ -0,0 +1,62 @@
|
|
1
|
+
Given /^that cucumber\-chef is installed$/ do
|
2
|
+
When 'I build the gem'
|
3
|
+
And 'I install the latest gem'
|
4
|
+
Then 'I should have cucumber-chef on my path'
|
5
|
+
end
|
6
|
+
|
7
|
+
When /^I display the config$/ do
|
8
|
+
@output = %x[cucumber-chef displayconfig 2>&1]
|
9
|
+
end
|
10
|
+
|
11
|
+
Then /^I should see config settings from knife\.rb$/ do
|
12
|
+
@output.should match /^chef_server_url: https:\/\/api.opscode.com\/organization/im
|
13
|
+
end
|
14
|
+
|
15
|
+
When /^I run a cucumber\-chef subcommand requiring Opscode and AWS credentials$/ do
|
16
|
+
@output = %x[cucumber-chef setup 2>&1]
|
17
|
+
end
|
18
|
+
|
19
|
+
When /^the config file contains invalid credentials$/ do
|
20
|
+
# see support/env.rb Around block
|
21
|
+
true
|
22
|
+
end
|
23
|
+
|
24
|
+
Then /^I should be alerted that my credentials are invalid$/ do
|
25
|
+
@output.should == "Invalid Opscode platform credentials. Please check.\n"
|
26
|
+
end
|
27
|
+
|
28
|
+
When /^I create a project called test_project$/ do
|
29
|
+
@project_name = "test_project"
|
30
|
+
project = "/tmp/cucumber-chef/#{@project_name}"
|
31
|
+
if File.exist?(project)
|
32
|
+
FileUtils.rm_rf(project)
|
33
|
+
end
|
34
|
+
silent_system("cd /tmp ; cucumber-chef project #{@project_name}").should be_true
|
35
|
+
end
|
36
|
+
|
37
|
+
project_dir = '/tmp/cucumber-chef/test_project'
|
38
|
+
features_dir = "#{project_dir}/features"
|
39
|
+
|
40
|
+
Then /^a new directory will be created named test_project$/ do
|
41
|
+
file_should_exist(project_dir)
|
42
|
+
end
|
43
|
+
|
44
|
+
Then /^it will contain directories for features, step_definitions, and support$/ do
|
45
|
+
%w[support step_definitions].each { |dir| file_should_exist("#{features_dir}/#{dir}") }
|
46
|
+
end
|
47
|
+
|
48
|
+
Then /^the support directory will contain essential libraries and helper imports$/ do
|
49
|
+
file_should_exist( "#{features_dir}/support/env.rb" )
|
50
|
+
file_should_contain( "#{features_dir}/support/env.rb",
|
51
|
+
"require 'cucumber/chef'\n" )
|
52
|
+
end
|
53
|
+
|
54
|
+
Then /^examples and documentation will be included$/ do
|
55
|
+
file_should_contain("#{project_dir}/README",
|
56
|
+
'Welcome to the test_project suite of cucumber-chef tests')
|
57
|
+
file_should_contain("#{features_dir}/example.feature",
|
58
|
+
'Feature: Example feature for test_project')
|
59
|
+
file_should_contain("#{features_dir}/step_definitions/example_step.rb",
|
60
|
+
'Given /^I apply the test_project role\/recipe$/ do')
|
61
|
+
end
|
62
|
+
|
@@ -0,0 +1,25 @@
|
|
1
|
+
#!/usr/bin/env ruby
|
2
|
+
|
3
|
+
$: << File.expand_path(File.join(File.dirname(__FILE__), '..', '..', 'lib'))
|
4
|
+
$: << File.expand_path(File.dirname(__FILE__))
|
5
|
+
|
6
|
+
require 'rspec/expectations'
|
7
|
+
require 'chef'
|
8
|
+
require 'cucumber/chef'
|
9
|
+
require 'cucumber/nagios/steps'
|
10
|
+
|
11
|
+
class CustomWorld
|
12
|
+
include Cucumber::Chef
|
13
|
+
end
|
14
|
+
|
15
|
+
World do
|
16
|
+
CustomWorld.new
|
17
|
+
end
|
18
|
+
|
19
|
+
Around('@invalid_credentials') do |scenario, block|
|
20
|
+
FileUtils.mkdir_p(".chef")
|
21
|
+
config = "chef_node_name 'REALLYBOGUSORGNAME'"
|
22
|
+
File.open(".chef/knife.rb", 'w') { |f| f.puts config }
|
23
|
+
block.call
|
24
|
+
FileUtils.rm_rf(".chef")
|
25
|
+
end
|
@@ -0,0 +1,26 @@
|
|
1
|
+
Feature: Usage of cucumber-chef command line tool
|
2
|
+
So that I can make use of cucumber-chef functionality
|
3
|
+
As a user
|
4
|
+
I can do really vague shit
|
5
|
+
|
6
|
+
Scenario: Show config
|
7
|
+
Given that cucumber-chef is installed
|
8
|
+
When I display the config
|
9
|
+
Then I should see config settings from knife.rb
|
10
|
+
|
11
|
+
@invalid_credentials
|
12
|
+
Scenario: Warn on bad credentials
|
13
|
+
Given that cucumber-chef is installed
|
14
|
+
But the config file contains invalid credentials
|
15
|
+
When I run a cucumber-chef subcommand requiring Opscode and AWS credentials
|
16
|
+
Then I should be alerted that my credentials are invalid
|
17
|
+
|
18
|
+
Scenario: Create a project
|
19
|
+
Given that cucumber-chef is installed
|
20
|
+
When I create a project called test_project
|
21
|
+
Then a new directory will be created named test_project
|
22
|
+
And it will contain directories for features, step_definitions, and support
|
23
|
+
And the support directory will contain essential libraries and helper imports
|
24
|
+
And examples and documentation will be included
|
25
|
+
|
26
|
+
|
@@ -0,0 +1 @@
|
|
1
|
+
require 'cucumber/chef' # compat
|
@@ -0,0 +1,195 @@
|
|
1
|
+
require "chef"
|
2
|
+
require "chef/cookbook_uploader"
|
3
|
+
require 'chef/knife'
|
4
|
+
require 'chef/knife/bootstrap'
|
5
|
+
require 'chef/knife/core/bootstrap_context'
|
6
|
+
require 'chef/knife/ssh'
|
7
|
+
require 'socket'
|
8
|
+
require 'net/ssh/multi'
|
9
|
+
require "fog"
|
10
|
+
require 'readline'
|
11
|
+
require 'stringio'
|
12
|
+
|
13
|
+
module Cucumber
|
14
|
+
module Chef
|
15
|
+
class Error < StandardError ; end
|
16
|
+
|
17
|
+
class ConfigError < Error ; end
|
18
|
+
class Config
|
19
|
+
KEYS = %w[node_name chef_server_url client_key validation_key validation_client_name]
|
20
|
+
KNIFE_KEYS = %w[aws_access_key_id aws_secret_access_key region availability_zone aws_ssh_key_id identity_file]
|
21
|
+
|
22
|
+
def config
|
23
|
+
full_path = Dir.pwd.split(File::SEPARATOR)
|
24
|
+
(full_path.length - 1).downto(0) do |i|
|
25
|
+
knife_file = File.join(full_path[0..i] + [".chef", "knife.rb"])
|
26
|
+
if File.exist?(knife_file)
|
27
|
+
::Chef::Config.from_file(knife_file)
|
28
|
+
return ::Chef::Config
|
29
|
+
end
|
30
|
+
end
|
31
|
+
raise ConfigError.new("Couldn't find knife.rb")
|
32
|
+
end
|
33
|
+
|
34
|
+
def display
|
35
|
+
current_config = config
|
36
|
+
values, missing_keys = [], []
|
37
|
+
KEYS.each do |key|
|
38
|
+
value = current_config[key]
|
39
|
+
if value && value != ""
|
40
|
+
values << "#{key}: #{value}"
|
41
|
+
else
|
42
|
+
missing_keys << key
|
43
|
+
end
|
44
|
+
end
|
45
|
+
KNIFE_KEYS.each do |key|
|
46
|
+
if value = current_config[:knife][key.to_sym]
|
47
|
+
values << "knife[:#{key}]: #{value}"
|
48
|
+
else
|
49
|
+
missing_keys << "knife[:#{key}]"
|
50
|
+
end
|
51
|
+
end
|
52
|
+
[values, missing_keys]
|
53
|
+
end
|
54
|
+
end
|
55
|
+
|
56
|
+
class ProvisionerError < Error ; end
|
57
|
+
class Provisioner
|
58
|
+
def initialize
|
59
|
+
@cookbook_path = File.join(File.dirname(__FILE__), "../../cookbooks/cucumber-chef")
|
60
|
+
end
|
61
|
+
|
62
|
+
def config
|
63
|
+
Config.new.config
|
64
|
+
end
|
65
|
+
|
66
|
+
def running_labs(connection, mode)
|
67
|
+
connection.servers.select {|s| s.tags['cucumber-chef'] == mode && s.state == 'running'}
|
68
|
+
end
|
69
|
+
|
70
|
+
def lab_exists?(connection, mode)
|
71
|
+
number_of_labs = running_labs(connection, mode).size
|
72
|
+
if number_of_labs > 0
|
73
|
+
return true
|
74
|
+
else
|
75
|
+
return false
|
76
|
+
end
|
77
|
+
end
|
78
|
+
|
79
|
+
def tag_server(connection, id, tag)
|
80
|
+
t = connection.tags.new
|
81
|
+
t.resource_id = id
|
82
|
+
t.key = "cucumber-chef"
|
83
|
+
t.value = tag
|
84
|
+
t.save
|
85
|
+
end
|
86
|
+
|
87
|
+
def bootstrap_node(dns_name, config)
|
88
|
+
template_file = File.join(File.dirname(__FILE__),
|
89
|
+
"chef/templates/ubuntu10.04-gems.erb")
|
90
|
+
bootstrap = ::Chef::Knife::Bootstrap.new
|
91
|
+
@stdout, @stderr, @stdout = StringIO.new, StringIO.new, StringIO.new
|
92
|
+
ui = ::Chef::Knife::UI.new(@stdout, @stderr, @stdout, bootstrap.config)
|
93
|
+
bootstrap.ui = ui
|
94
|
+
bootstrap.name_args = [dns_name]
|
95
|
+
bootstrap.config[:run_list] = "role[test_lab_test]"
|
96
|
+
bootstrap.config[:ssh_user] = "ubuntu"
|
97
|
+
bootstrap.config[:identity_file] = config[:knife][:identity_file]
|
98
|
+
bootstrap.config[:chef_node_name] = "cucumber-chef-test-lab"
|
99
|
+
bootstrap.config[:use_sudo] = true
|
100
|
+
bootstrap.config[:template_file] = template_file
|
101
|
+
bootstrap.config[:validation_client_name] = config["validation_client_name"]
|
102
|
+
bootstrap.config[:validation_key] = config["validation_key"]
|
103
|
+
bootstrap.config[:chef_server_url] = config["chef_server_url"]
|
104
|
+
bootstrap
|
105
|
+
end
|
106
|
+
|
107
|
+
def build_controller(dns_name, config)
|
108
|
+
template_file = File.join(File.dirname(__FILE__),
|
109
|
+
"chef/templates/controller.erb")
|
110
|
+
bootstrap = ::Chef::Knife::Bootstrap.new
|
111
|
+
@stdout, @stderr, @stdout = StringIO.new, StringIO.new, StringIO.new
|
112
|
+
ui = ::Chef::Knife::UI.new(@stdout, @stderr, @stdout, bootstrap.config)
|
113
|
+
bootstrap.ui = ui
|
114
|
+
bootstrap.name_args = [dns_name]
|
115
|
+
bootstrap.config[:ssh_user] = "ubuntu"
|
116
|
+
bootstrap.config[:identity_file] = config[:knife][:identity_file]
|
117
|
+
bootstrap.config[:chef_node_name] = "cucumber-chef-controller"
|
118
|
+
bootstrap.config[:use_sudo] = true
|
119
|
+
bootstrap.config[:template_file] = template_file
|
120
|
+
bootstrap.config[:validation_client_name] = config["validation_client_name"]
|
121
|
+
bootstrap.config[:validation_key] = config["validation_key"]
|
122
|
+
bootstrap.config[:chef_server_url] = config["chef_server_url"]
|
123
|
+
bootstrap
|
124
|
+
end
|
125
|
+
|
126
|
+
def verify_opscode_platform_credentials(config)
|
127
|
+
username = config['node_name']
|
128
|
+
if username
|
129
|
+
req = Net::HTTP.new('community.opscode.com', 80)
|
130
|
+
code = req.request_head("/users/#{username}").code
|
131
|
+
end
|
132
|
+
if username == "" || code != "200"
|
133
|
+
raise ProvisionerError.new("Invalid Opscode platform credentials. Please check.")
|
134
|
+
end
|
135
|
+
end
|
136
|
+
|
137
|
+
def verify_aws_credentials(config)
|
138
|
+
compute = Fog::Compute.new(:provider => 'AWS',
|
139
|
+
:aws_access_key_id => config[:knife][:aws_access_key_id],
|
140
|
+
:aws_secret_access_key => config[:knife][:aws_secret_access_key])
|
141
|
+
compute.describe_availability_zones
|
142
|
+
rescue Fog::Service::Error => err
|
143
|
+
raise ProvisionerError.new("Invalid AWS credentials. Please check.")
|
144
|
+
end
|
145
|
+
|
146
|
+
def upload_cookbook(config)
|
147
|
+
version_loader = ::Chef::Cookbook::CookbookVersionLoader.new(@cookbook_path)
|
148
|
+
version_loader.load_cookbooks
|
149
|
+
uploader = ::Chef::CookbookUploader.new(version_loader.cookbook_version,
|
150
|
+
@cookbook_path)
|
151
|
+
uploader.upload_cookbook
|
152
|
+
end
|
153
|
+
|
154
|
+
def upload_role(config)
|
155
|
+
role_path = File.join(@cookbook_path, "roles")
|
156
|
+
::Chef::Config[:role_path] = role_path
|
157
|
+
role = ::Chef::Role.from_disk("test_lab_test")
|
158
|
+
role.save
|
159
|
+
role = ::Chef::Role.from_disk("controller")
|
160
|
+
role.save
|
161
|
+
end
|
162
|
+
|
163
|
+
def build_test_lab(config, output)
|
164
|
+
connection = Fog::Compute.new(:provider => 'AWS',
|
165
|
+
:aws_access_key_id => config[:knife][:aws_access_key_id],
|
166
|
+
:aws_secret_access_key => config[:knife][:aws_secret_access_key],
|
167
|
+
:region => config[:knife][:region])
|
168
|
+
mode = config["mode"]
|
169
|
+
if lab_exists?(connection, mode)
|
170
|
+
raise ProvisionerError.new("A test lab already exists using the AWS credentials you supplied")
|
171
|
+
end
|
172
|
+
ami = connection.images.get("ami-339ca947")
|
173
|
+
server_def = { :image_id => "ami-339ca947", :groups => "default", :flavor_id => "m1.small", :key_name => config[:knife][:aws_ssh_key_id], :availability_zone => config[:knife][:availability_zone], :tags => {"purpose" => "cucumber-chef"}, :identity_file => config[:knife][:identity_file] }
|
174
|
+
server = connection.servers.create(server_def)
|
175
|
+
output.puts "Provisioning cucumber-chef test lab platform."
|
176
|
+
output.print "Waiting for server"
|
177
|
+
server.wait_for { output.print "."; ready? }
|
178
|
+
output.puts("\n")
|
179
|
+
tag_server(connection, server.id, config["mode"])
|
180
|
+
output.puts "Instance ID: #{server.id} ; IP Address #{server.public_ip_address}"
|
181
|
+
output.puts "Platform provisioned. Run cucumber-chef project to get started."
|
182
|
+
server
|
183
|
+
end
|
184
|
+
end
|
185
|
+
end
|
186
|
+
end
|
187
|
+
|
188
|
+
begin
|
189
|
+
require 'cucumber/chef/version'
|
190
|
+
rescue LoadError => e
|
191
|
+
dep = e.message.split.last
|
192
|
+
puts "You don't appear to have #{dep} installed."
|
193
|
+
puts "Perhaps run `gem bundle` or `gem install #{dep}`?"
|
194
|
+
exit 2
|
195
|
+
end
|