dev-lxc 0.1.2

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.
@@ -0,0 +1,261 @@
1
+ # Authors
2
+ # Seth Chisamore
3
+ # Seth Falcon
4
+
5
+ # OPC config data
6
+ # TODO - read this in from /etc/opscode/chef-server-running.json
7
+ opc_bundle = "#{PiabHelper.omnibus_root}/embedded/bin/bundle"
8
+ opscode_account_url = "http://127.0.0.1:9465"
9
+ opscode_account_path = "#{PiabHelper.omnibus_root}/embedded/service/opscode-account"
10
+ superuser_pem = "/etc/opscode/pivotal.pem"
11
+ superuser_name = ::File.basename(superuser_pem).split('.')[0]
12
+ user_root = "/srv/piab/users"
13
+ dev_users = {}
14
+
15
+ organizations = {
16
+ 'ponyville' => [
17
+ 'rainbowdash',
18
+ 'fluttershy',
19
+ 'applejack',
20
+ 'pinkiepie',
21
+ 'twilightsparkle',
22
+ 'rarity'
23
+ ],
24
+ 'wonderbolts' => [
25
+ 'spitfire',
26
+ 'soarin',
27
+ 'rapidfire',
28
+ 'fleetfoot'
29
+ ]
30
+ }
31
+
32
+ organizations.each do |orgname, users|
33
+
34
+ users.each do |username|
35
+
36
+ folder = "#{user_root}/#{username}"
37
+ dot_chef = "#{folder}/.chef"
38
+
39
+ dev_users[username] = {
40
+ 'username' => username,
41
+ 'displayname' => username,
42
+ 'email' => "#{username}@mylittlepony.com",
43
+ 'orgname' => orgname,
44
+ 'folder' => folder,
45
+ 'private_key' => "#{dot_chef}/#{username}.pem",
46
+ 'org_validator' => "#{dot_chef}/#{username}-validator.pem",
47
+ 'knife_config' => "#{dot_chef}/knife.rb"
48
+ }
49
+
50
+ end
51
+ end
52
+
53
+ unless File.exists?("/srv/piab/dev_users_created")
54
+
55
+ ruby_block "Waiting for first-time OPC initializtion" do
56
+ block do
57
+ sleep 10
58
+ end
59
+ end
60
+
61
+ dev_users.each_pair do |name, options|
62
+
63
+ # create the students .chef/ dir
64
+ directory ::File.dirname(options['private_key']) do
65
+ recursive true
66
+ action :create
67
+ end
68
+
69
+ # create an account on the OPC for the student
70
+ execute "create OPC account #{name}" do
71
+ command <<-EOH
72
+ #{opc_bundle} exec bin/createobjecttool --object-type 'user' -a '#{opscode_account_url}' \
73
+ --object-name #{options['username']} --displayname '#{options['displayname']}' -e '#{options['email']}' \
74
+ -f '#{options['displayname']}' -m '#{options['displayname']}' -l '#{options['displayname']}' \
75
+ --key-path #{options['private_key']} --user-password '#{options['username']}' \
76
+ --opscode-username #{superuser_name} --opscode-private-key #{superuser_pem}
77
+ EOH
78
+ cwd opscode_account_path
79
+ end
80
+
81
+ # create a knife.rb file for the user
82
+ template "#{options['knife_config']}" do
83
+ source "knife.rb.erb"
84
+ variables(
85
+ :username => options['username'],
86
+ :orgname => options['orgname'],
87
+ :server_fqdn => 'chef.lxc'
88
+ )
89
+ mode "0777"
90
+ action :create
91
+ end
92
+
93
+ end
94
+
95
+ # create the orgs and associate the users
96
+ organizations.each do |orgname, users|
97
+
98
+ org_validator = "#{user_root}/#{orgname}-validator.pem"
99
+
100
+ ruby_block "create OPC organization #{orgname}" do
101
+ block do
102
+ cmd =<<-EOH
103
+ #{opc_bundle} exec bin/createorgtool -t Business -a '#{opscode_account_url}' \
104
+ --org-name #{orgname} --customer-org-fullname '#{orgname}' \
105
+ --username '#{users.join(' ')}' \
106
+ --client-key-path #{org_validator} \
107
+ --opscode-username #{superuser_name} --opscode-private-key #{superuser_pem}
108
+ EOH
109
+ waiting = true
110
+ while waiting
111
+ opts = {:cwd => opscode_account_path,
112
+ :returns => [0,53]}
113
+ case shell_out(cmd, opts).exitstatus
114
+ when 53
115
+ Chef::Log.info("...")
116
+ sleep 10
117
+ when 0
118
+ Chef::Log.info("#{orgname} created!")
119
+ waiting = false
120
+ else
121
+ Chef::Log.error("#{orgname} not created...error!")
122
+ waiting = false
123
+ end
124
+ end
125
+ end
126
+ end
127
+
128
+ end
129
+
130
+ ruby_block 'LOL' do
131
+ block do
132
+ Chef::Log.info <<-EOH
133
+
134
+
135
+ .`
136
+ `,,,,,.` ;,;
137
+ ,;;;;;''''';;;,:..; ` ;;
138
+ .;;;'''''''''''''';,...; ;;; ;,;
139
+ ` ,;;;''''''''''''';;;;;,....; ;:,; ;..;
140
+ ;;''''''';'''''';;;;;;;:,....,; ;,,,; ;:,,..;
141
+ :;;;;'';''''';;;;;;;;;,,.....:. `;,,,: ;,,:..,,
142
+ ```;'''';;;;;;;;;;..,...;..; ;,,,: :,,;..,:`
143
+ ;''';;;;;;;;;;;.,,:....:.,: ;,,,; :,,:...; :;;;
144
+ ;''';;;;;;;;;;:,,,,;....;..;;` .,,,,: :,,;....; .:...;
145
+ ,;';;;;;;;;;;;,,,,.;,....,,.,:;. ;,,,,. ;,,;...,: ;....;
146
+ `;';;;;;;;;;;;,,,,,,;......:..';;. ;,,,: `,,,:...:` .;....,,
147
+ ;';;;;;;;;;;;,,,,,,,,.....:;.,;;;; ;,,,: ;,,:,...; ;;.....;
148
+ ,;;;;;;;;;;;;;,,,:,,'......,,..;;;'; ;,,,; ;,,:....;.::....:
149
+ ;;;;;;;;;;;;;.,,,'.:...........;;;;; ;,,,; ;,,;....;;'....,:
150
+ ,;;;;;;;;;;;;,,,,,:,:...........:;;;;. ;,,,: ;,,'....',,....;
151
+ ;;;;;;;;;;;;;,,,,;,;............,:;;'; ;,,,:,:,,;....';....,.
152
+ `:;;;;;;;;;;;.,,,';;.........,....';;;; ;,,,,;:,,:,...;:....;
153
+ ;;;;;;;;;;;;;,,,;.;...........,...;;;;; ;,,,,;:,,:....;....,`
154
+ ;;;;;;;;;;;;,,,;,,.+......;,':.;..:';;; ;,,,,;,,:,....:....;
155
+ .;;;;;;:;;@;#,,'...;......@@@@:@,..,;;;; :,,,,::,;.........,,
156
+ ;;;;;;;;;;+;;,;....,...,,@@@@@@.@..,;;;; .:,,,,;,'.........; .;
157
+ :;;;::;;;';@#;.........'# +@@@@;...,;;;;, ;,,,,,,;........,; ,;;;: ;;;
158
+ ;;;;; ;;;;;#;,'...,@...@;` `\#@@@....,;;;'; ;,,,:;,;..;;....;` ;,...,: .;;; .:;;;;;;;;;;,
159
+ `:;;. :;;;+';,: ,..,;@@+ : `\#@@@....:;;;;;` ;,,:,,::.'..,...;;,......:;;;; .;;'''''''''''''';;`
160
+ ;:: ;;;;;.@@: @....;; ;. ;@@@#....;;;;;;; ;,:,,,;,'..,,..::........;'';,;;'''''''''';;:::,,,,,
161
+ .: ,;;;` + ;' @....,,` :;+@@@@'..,:;;;;;;;.,,,,,,;:...,...'........;'';;'''''''''''';,
162
+ ;:: :'#:.....; `;;\#.\#@:..,;;;;;;;;;`:,,,,;:...;...........;;';;''''''';;;;'''';:
163
+ ;: + @'.....@ ';;:;;;.,;;;;;;;;;;;:,,,,;...,:,........,;;'';''';;;;;;;;;;;;''';
164
+ : `;@+,.....@ ';,...,;;;;;;';;;;;:,,,:,...;,:,......:;''';;;;;;;;;;;;;;;;;;''';
165
+ ` '::.......',..,...;;;;;;;;;;;;;,,,,;...;,...:,..,;;'''';;;;;;;;;;;;;;;;;;;''';
166
+ '........,:,,...;;';;;;;;;;;';:,,,,..;....,,.,;,,;;'';;;;;;;;;;;;;;;;;;;;;''';
167
+ ;,.........,....:;;:;;;;;;;;;';:,,;..:.....;.,::,..,:;;;;;;;;;;;;;;;;;;;;;;;''';
168
+ .,.,..,..........;,;;;;;;;;;;''';,'........'..........;;;;;;;;;;;;;;;;;;';;;;'''';
169
+ ;....;.........,,:;;;;;;;;;'''';;........;,,,,......:';;;;;::::;;';;;;;;';;;;'''':
170
+ ;;;;..........;,:;;;;;;;;;'''';,......,;,...,,....;,.,,,,,,,,,,,,,;';;;;;;;;;''';`
171
+ `;,........,;;..;;;;;;;;;'''';.......,:.....;...,;;;;;::,,,..,,,,,,.;;;;;;;;;;''';
172
+ .;;;;;;;;. :,:;;;;;;;;'';'';.......,,....,,.,;:;;;;;;;;;;;;;:.,,,,,,;;;;;;;;''';`
173
+ ;..;;;;;;;;;;;'';..............;:;;;'''''''''''';;;;;.,,,,:;;;;;;;;''';
174
+ ;,:;;;;;;;;;;'';............,:;;..;';;:::;;''''''';;;;,,,,.';;;;;;;''';
175
+ :,.;;;;;;;;;;'';.........,,:;:,....,; :;''''''';;;:,,,;;;;;;;;;'';
176
+ ;.:;;;;;;;::'';....;.,.....,,,......:, `;''';''';;;,,,:;;;;;;;;'';
177
+ `:.;;;;;;;.:';;......;:.....,:, :...; :''';:''';;;.,,;;;;;;;;;';
178
+ :.:;;;;:.,,;;,.........,:;;:,, ...,` ;''; ;'';;;:,.;;;;;;;;;';
179
+ ;.;;;:...,;;...............` , .....; ;''; :''';;;,.';;;;;;;;';
180
+ ;;;;....,;;..............,, , `.:...; .''; ;'';;;.,';;;;;,;;';
181
+ `;;,.....;,................, ` ..,:` .''; ;'';;;.,;;;;;;; ;;;
182
+ .;..........................,:` , ....:` :''; :'';;;.,:;;;;;; `;;
183
+ ,............................,',,;.,....,` ;'; ;'';;;.,:;;;;;; ;;
184
+ ,............................,'.,:,;....:` .;;: ;'';;;.,:;;;;;: `;
185
+ ,............................,',,,,:...,; ;;, .''';;;,,:;;;;;. ;
186
+ .,....................,;,.....';'',:....; ;;. ;''';;;,,:;;;;;` ;
187
+ :......................;.....;'::,,...,: .; ;'';;;;,,,;;;;;, ,
188
+ :;;. ;......................::....,:.,,,..,:` ;'';;;;,,,;;;;;;
189
+ ;,,;;;:::;;,;.,....................;,......,,,...; ;'';;;;,,,;;;;;;
190
+ ;,,,,,,,,,,,:,:,....................;,.....,:,....;` .''';;;;.,,;;;;;;
191
+ `:,,,,,,,,,,,,;:......,............,;:;......:......;;. ,''';;;;.,,;;;;;;
192
+ :,,,,,,,,,,,,,,;......'.........,;; ;,:;,....,........:;;:` :''';;;;.,,;;;;;;
193
+ ;,,,,,,,,,,,,,,;......;,....,,;;, ;,,;;,..............,;, ;''';;;;,,,;;;;;:
194
+ ;,,,,,,,,,,,,,,:.....,:,::::,` ;,,,:;,..............;` ;''';;;:,,,;;;;;.
195
+ .:,,,,,:,:;;;;;;,......,` ;:,,,:;;,...........,; ;''';;::,,:;;;;;
196
+ ;,,,,,,::` ;.......,, ,;,,,,,;;,..........:; ;''';;;,,,:;;;;;
197
+ ;,,,,,,:` ;.......,: ;:,,,,,;;,.........; ;''';;:.,,;;;;;,
198
+ ;,,,,,,,: :........: .;,,,,,,;.........,; ;''';;;.,,;;;;;
199
+ ,:,,,,,,,; ,,........; ::,,,,,,;.........; ;'''':;.,,';;;;
200
+ ;,,,,,,,,:` ;.........; ;,,,,,,:,........:;,;''':;.,,';;;:
201
+ ;,,,,,,,,,; ;.........: ;,,,,,,,;.........; ;''';;.,,';;;,
202
+ ;,,,,,,,,,;` ,.........: ;,,,,,,,:;........;.,'''';,,,';;;.
203
+ ;,,,,,,,,,,; ..........,, :,,,,,,,,;........,; ;'''.;,,;;;;,
204
+ ;,,,,,,,,,,;, ;.........,. :,,,,,,,,;.........;` ;'';`;,,;;;:
205
+ `:,,,,,,,,,,,; :.........,` :,,,,,,,,;,........:; ,;'; ,:.'';;
206
+ `:,,,,,,,,,,,;;,.........: ;,,,,,,,,::.........; :;; ::';;;
207
+ `:,,,,,,,,,,,,;.........,; ;,,,,,,,,:;,........;: :': ::;;;`
208
+ :,,,,,,,,,,,,:,.........; ;,,,,,,,,:;.........,; :; ,;;;;
209
+ ;,,,,,,,,,,,;...........; `:,,,,,,,,:;..........;. ,; ,;;;
210
+ ;,,,,,,,,,,,:,..........; :,,,,,,,,,;;..........:; ,: ,;;;
211
+ :,,,,,,,,,,;...........,. ;,,,,,,,,,;;..........,; `: ,;;
212
+ ;,,,,,,,,,,...........:` ;,,,,,,,,,;;...........; :;,
213
+ ;,,,,,,,,;............; .;,,,,,,,,,;;...........;. ;:
214
+ `:,,,,,,:.............; ;,,,,,,,,,,:;..........,:: .,
215
+ ;,,,,,;:............,: ;,,,,,,,,,,,;...........:: `
216
+ ;,,;;:.............:` ;,,,,,,,,,,`;...........,;
217
+ :, :.............; ,,,,,,,,,,,: ;,..........,;
218
+ ;..............; ;,,,,,,,,,,:,:............;
219
+ .:.............,` `;,,,,,,,,,,;;,............;`
220
+ ;..............; ;,,,,,,,,,,,.;............,:`
221
+ :,.............., `;,,,,:::::;;`;........,...:;
222
+ :..............: ,,,,,..`` :...,,,::;;;;.
223
+ ;;;::::::::::;;;; ,;;:`
224
+
225
+ . t#, L. .,
226
+ ;W ;##W. EW: ,ft t ,Wt
227
+ f#E :#L:WE E##; t#E Ej i#D.
228
+ .E#f .KG ,#D E###t t#E E#, f#f
229
+ iWW; EE ;#f E#fE#f t#E E#t .D#i
230
+ L##Lffi f#. t#i E#t D#G t#E E#t :KW, .......
231
+ tLLG##L :#G GK E#t f#E. t#E E#t t#f GEEEEEEf.
232
+ ,W#i ;#L LW. E#t t#K: t#E E#t ;#G
233
+ j#E. t#f f#: E#t ;#W,t#E E#t :KE.
234
+ .D#j f#D#; E#t :K#D#E E#t .DW:
235
+ ,WK, G#t E#t .E##E E#t L#,
236
+ EG. t .. G#E E#t jt
237
+ , fE ,;.
238
+ ,
239
+ L. t#, t#,
240
+ j. t EW: ,ft . ;##W. ;##W.
241
+ EW, .. Ej E##; t#E Ef. :#L:WE :#L:WE .. :
242
+ E##j ;W, E#, E###t t#E E#Wi .KG ,#D .KG ,#D ,W, .Et
243
+ E###D. j##, E#t E#fE#f t#E E#K#D: EE ;#f EE ;#f t##, ,W#t
244
+ E#jG#W; G###, E#t E#t D#G t#E E#t,E#f. f#. t#i f#. t#i L###, j###t
245
+ E#t t##f :E####, E#t E#t f#E. t#E E#WEE##Wt:#G GK :#G GK .E#j##, G#fE#t
246
+ E#t :K#E: ;W#DG##, E#t E#t t#K: t#E E##Ei;;;;.;#L LW. ;#L LW. ;WW; ##,:K#i E#t
247
+ E#KDDDD###i j###DW##, E#t E#t ;#W,t#E E#DWWt t#f f#: t#f f#: j#E. ##f#W, E#t
248
+ E#f,t#Wi,,, G##i,,G##, E#t E#t :K#D#E E#t f#K; f#D#; f#D#; .D#L ###K: E#t
249
+ E#t ;#W: :K#K: L##, E#t E#t .E##E E#Dfff##E, G#t G#t :K#t ##D. E#t
250
+ DWi ,KK: ;##D. L##, E#t .. G#E jLLLLLLLLL; t t ... #G ..
251
+ ,,, .,, ,;. fE j
252
+ ,
253
+ EOH
254
+ end
255
+ end
256
+
257
+ file "/srv/piab/dev_users_created" do
258
+ content "Canned dev users and organization created successfully at #{Time.now}"
259
+ action :create
260
+ end
261
+ end
@@ -0,0 +1,15 @@
1
+ # Authors
2
+ # Seth Chisamore
3
+ # Mark Mzyk
4
+
5
+ current_dir = File.dirname(__FILE__)
6
+ log_level :info
7
+ log_location STDOUT
8
+ node_name "<%= @username %>"
9
+ client_key "#{current_dir}/<%= @username %>.pem"
10
+ validation_client_name "<%= @orgname %>-validator"
11
+ validation_key "#{current_dir}/../../<%= @orgname %>-validator.pem"
12
+ chef_server_url "https://<%= @server_fqdn %>/organizations/<%= @orgname %>"
13
+ cache_type 'BasicFile'
14
+ cache_options( :path => "#{ENV['HOME']}/.chef/checksums" )
15
+ cookbook_path ["#{current_dir}/../cookbooks"]
@@ -0,0 +1,127 @@
1
+ require "dev-lxc/chef-server"
2
+
3
+ module DevLXC
4
+ class ChefCluster
5
+ attr_reader :api_fqdn, :topology, :bootstrap_backend, :secondary_backend, :frontends
6
+
7
+ def initialize(cluster_config)
8
+ @cluster_config = cluster_config
9
+ @api_fqdn = @cluster_config["api_fqdn"]
10
+ @topology = @cluster_config["topology"]
11
+ @servers = @cluster_config["servers"]
12
+ if %w(tier ha).include?(@topology)
13
+ @bootstrap_backend = @servers.select {|k,v| v["role"] == "backend" && v["bootstrap"] == true}.first.first
14
+ @frontends = @servers.select {|k,v| v["role"] == "frontend"}.keys
15
+ end
16
+ if @topology == "ha"
17
+ @secondary_backend = @servers.select {|k,v| v["role"] == "backend" && v["bootstrap"] == nil}.first.first
18
+ end
19
+ end
20
+
21
+ def chef_servers
22
+ chef_servers = Array.new
23
+ case @topology
24
+ when "open-source", "standalone"
25
+ chef_servers << ChefServer.new(@servers.keys.first, @cluster_config)
26
+ when "tier"
27
+ chef_servers << ChefServer.new(@bootstrap_backend, @cluster_config)
28
+ @frontends.each do |frontend_name|
29
+ chef_servers << ChefServer.new(frontend_name, @cluster_config)
30
+ end
31
+ when "ha"
32
+ chef_servers << ChefServer.new(@bootstrap_backend, @cluster_config)
33
+ chef_servers << ChefServer.new(@secondary_backend, @cluster_config)
34
+ @frontends.each do |frontend_name|
35
+ chef_servers << ChefServer.new(frontend_name, @cluster_config)
36
+ end
37
+ end
38
+ chef_servers
39
+ end
40
+
41
+ def status
42
+ puts "Cluster is available at https://#{@api_fqdn}"
43
+ chef_servers.each { |cs| cs.status }
44
+ end
45
+
46
+ def abspath(rootfs_path)
47
+ abspath = Array.new
48
+ chef_servers.each { |cs| abspath << cs.abspath(rootfs_path) }
49
+ abspath.compact
50
+ end
51
+
52
+ def run_command(command)
53
+ chef_servers.each { |cs| cs.run_command(command) }
54
+ end
55
+
56
+ def start
57
+ puts "Starting cluster"
58
+ chef_servers.each { |cs| cs.start }
59
+ end
60
+
61
+ def stop
62
+ puts "Stopping cluster"
63
+ chef_servers.reverse_each { |cs| cs.stop }
64
+ end
65
+
66
+ def destroy
67
+ puts "Destroying cluster"
68
+ chef_servers.reverse_each { |cs| cs.destroy }
69
+ end
70
+
71
+ def destroy_base_containers
72
+ @servers.keys.each do |server_name|
73
+ DevLXC::Container.new("b-#{server_name}").destroy
74
+ end
75
+ DevLXC::Container.new(DevLXC::ChefServer.new(@servers.keys.first, @cluster_config).base_server_name).destroy
76
+ end
77
+
78
+ def chef_server_config
79
+ chef_server_config = %Q(api_fqdn "#{@api_fqdn}"\n)
80
+ @cluster_config["packages"]["server"].to_s.match(/(private-chef|chef-server)[_-](\d+)\.(\d+\.?){2,}-/)
81
+ if Regexp.last_match[2].to_i >= 11
82
+ chef_server_config += %Q(bookshelf["vip"] = "#{@api_fqdn}"\n)
83
+ end
84
+ if %w(tier ha).include?(@topology)
85
+ chef_server_config += %Q(
86
+ topology "#{@topology}"
87
+
88
+ server "#{@bootstrap_backend}",
89
+ :ipaddress => "#{@servers[@bootstrap_backend]["ipaddress"]}",
90
+ :role => "backend",
91
+ :bootstrap => true)
92
+
93
+ case @topology
94
+ when "tier"
95
+ chef_server_config += %Q(
96
+
97
+ backend_vip "#{@bootstrap_backend}",
98
+ :ipaddress => "#{@servers[@bootstrap_backend]["ipaddress"]}"
99
+ )
100
+ when "ha"
101
+ backend_vip_name = config["backend_vip"].keys.first
102
+ chef_server_config += %Q(,
103
+ :cluster_ipaddress => "#{@servers[@bootstrap_backend]["cluster_ipaddress"]}"
104
+
105
+ server "#{@secondary_backend}",
106
+ :ipaddress => "#{@servers[@secondary_backend]["ipaddress"]}",
107
+ :role => "backend",
108
+ :cluster_ipaddress => "#{@servers[@secondary_backend]["cluster_ipaddress"]}
109
+
110
+ backend_vip "#{backend_vip_name}",
111
+ :ipaddress => "#{config["backend_vip"][backend_vip_name]["ipaddress"]}",
112
+ :device => "#{config["backend_vip"][backend_vip_name]["device"]}",
113
+ :heartbeat_device => "#{config["backend_vip"][backend_vip_name]["heartbeat_device"]}"
114
+ )
115
+ end
116
+ @frontends.each do |frontend_name|
117
+ chef_server_config += %Q(
118
+ server "#{frontend_name}",
119
+ :ipaddress => "#{@servers[frontend_name]["ipaddress"]}",
120
+ :role => "frontend"
121
+ )
122
+ end
123
+ end
124
+ return chef_server_config
125
+ end
126
+ end
127
+ end
@@ -0,0 +1,234 @@
1
+ require "dev-lxc/container"
2
+ require "dev-lxc/chef-cluster"
3
+
4
+ module DevLXC
5
+ class ChefServer
6
+ attr_reader :base_platform, :base_server_name
7
+
8
+ def initialize(name, cluster_config)
9
+ unless cluster_config["servers"].keys.include?(name)
10
+ raise "Server #{name} is not defined in the cluster config"
11
+ end
12
+ cluster = DevLXC::ChefCluster.new(cluster_config)
13
+ @server = DevLXC::Container.new(name)
14
+ @config = cluster_config["servers"][@server.name]
15
+ @ipaddress = @config["ipaddress"]
16
+ case cluster.topology
17
+ when "open-source", "standalone"
18
+ @role = cluster.topology
19
+ when "tier", "ha"
20
+ @role = "bootstrap_backend" if @server.name == cluster.bootstrap_backend
21
+ @role = "secondary_backend" if @server.name == cluster.secondary_backend
22
+ @role = "frontend" if cluster.frontends.include?(@server.name)
23
+ end
24
+ @mounts = cluster_config["mounts"]
25
+ @bootstrap_backend = cluster.bootstrap_backend
26
+ @chef_server_config = cluster.chef_server_config
27
+ @api_fqdn = cluster.api_fqdn
28
+ @base_platform = cluster_config["base_platform"]
29
+ @packages = cluster_config["packages"]
30
+
31
+ @base_server_name = @base_platform
32
+ @base_server_name += "-ec-#{Regexp.last_match[1].gsub(".", "-")}" if @packages["server"].to_s.match(/private-chef[_-]((\d+\.?){3,})-/)
33
+ @base_server_name += "-osc-#{Regexp.last_match[1].gsub(".", "-")}" if @packages["server"].to_s.match(/chef-server[_-]((\d+\.?){3,})-/)
34
+ @base_server_name += "-reporting-#{Regexp.last_match[1].gsub(".", "-")}" if @packages["reporting"].to_s.match(/[_-]((\d+\.?){3,})-/)
35
+ @base_server_name += "-pushy-#{Regexp.last_match[1].gsub(".", "-")}" if @packages["push-jobs-server"].to_s.match(/[_-]((\d+\.?){3,})-/)
36
+ end
37
+
38
+ def status
39
+ if @server.defined?
40
+ state = @server.state
41
+ ip_addresses = @server.ip_addresses.join(" ") if @server.state == :running
42
+ else
43
+ state = "not_created"
44
+ end
45
+ printf "%20s %-15s %s\n", @server.name, state, ip_addresses
46
+ end
47
+
48
+ def abspath(rootfs_path)
49
+ "#{@server.config_item('lxc.rootfs')}#{rootfs_path}" if @server.defined?
50
+ end
51
+
52
+ def run_command(command)
53
+ if @server.running?
54
+ puts "Running '#{command}' in #{@server.name}"
55
+ @server.run_command(command)
56
+ else
57
+ puts "#{@server.name} is not running"
58
+ end
59
+ end
60
+
61
+ def start
62
+ create
63
+ hwaddr = @server.config_item("lxc.network.0.hwaddr")
64
+ DevLXC.assign_ip_address(@ipaddress, @server.name, hwaddr)
65
+ DevLXC.create_dns_record(@api_fqdn, @server.name, @ipaddress) if %w(open-source standalone frontend).include?(@role)
66
+ @server.sync_mounts(@mounts)
67
+ @server.start
68
+ end
69
+
70
+ def stop
71
+ hwaddr = @server.config_item("lxc.network.0.hwaddr") if @server.defined?
72
+ @server.stop
73
+ deregister_from_dnsmasq(hwaddr)
74
+ end
75
+
76
+ def destroy
77
+ hwaddr = @server.config_item("lxc.network.0.hwaddr") if @server.defined?
78
+ @server.destroy
79
+ deregister_from_dnsmasq(hwaddr)
80
+ end
81
+
82
+ def deregister_from_dnsmasq(hwaddr)
83
+ DevLXC.search_file_delete_line("/etc/lxc/addn-hosts.conf", /^#{@ipaddress}\s/)
84
+ DevLXC.search_file_delete_line("/etc/lxc/dhcp-hosts.conf", /,#{@ipaddress}$/)
85
+ unless hwaddr.nil?
86
+ DevLXC.search_file_delete_line("/etc/lxc/dhcp-hosts.conf", /^#{hwaddr}/)
87
+ end
88
+ DevLXC.reload_dnsmasq
89
+ end
90
+
91
+ def destroy_base_containers
92
+ DevLXC::Container.new("b-#{@server.name}").destroy
93
+ DevLXC::Container.new(@base_server_name).destroy
94
+ DevLXC::Container.new(@base_platform).destroy
95
+ end
96
+
97
+ def create
98
+ if @server.defined?
99
+ puts "Using existing container #{@server.name}"
100
+ return
101
+ end
102
+ server_clone = DevLXC::Container.new("b-#{@server.name}")
103
+ if server_clone.defined?
104
+ puts "Cloning container #{server_clone.name} into container #{@server.name}"
105
+ server_clone.clone(@server.name, {:flags => LXC::LXC_CLONE_SNAPSHOT|LXC::LXC_CLONE_KEEPMACADDR})
106
+ @server = DevLXC::Container.new(@server.name)
107
+ return
108
+ else
109
+ puts "Creating container #{@server.name}"
110
+ unless %w(open-source standalone).include?(@role) || @server.name == @bootstrap_backend || DevLXC::Container.new(@bootstrap_backend).defined?
111
+ raise "The bootstrap backend server must be created first."
112
+ end
113
+ base_server = create_base_server
114
+ puts "Cloning container #{base_server.name} into container #{@server.name}"
115
+ base_server.clone(@server.name, {:flags => LXC::LXC_CLONE_SNAPSHOT})
116
+ @server = DevLXC::Container.new(@server.name)
117
+ puts "Adding lxc.hook.post-stop hook"
118
+ @server.set_config_item("lxc.hook.post-stop", "/usr/local/share/lxc/hooks/post-stop-dhcp-release")
119
+ @server.save_config
120
+ hwaddr = @server.config_item("lxc.network.0.hwaddr")
121
+ raise "#{@server.name} needs to have an lxc.network.hwaddr entry" if hwaddr.empty?
122
+ DevLXC.assign_ip_address(@ipaddress, @server.name, hwaddr)
123
+ DevLXC.create_dns_record(@api_fqdn, @server.name, @ipaddress) if %w(open-source standalone frontend).include?(@role)
124
+ @server.sync_mounts(@mounts)
125
+ @server.start
126
+ configure_server unless @packages["server"].nil?
127
+ create_users if %w(standalone bootstrap_backend).include?(@role)
128
+ if %w(standalone bootstrap_backend secondary_backend frontend).include?(@role)
129
+ configure_reporting unless @packages["reporting"].nil?
130
+ configure_push_jobs_server unless @packages["push-jobs-server"].nil?
131
+ end
132
+ if %w(standalone frontend).include?(@role) && ! @packages["manage"].nil?
133
+ @server.install_package(@packages["manage"])
134
+ configure_manage
135
+ end
136
+ @server.stop
137
+ puts "Cloning container #{@server.name} into b-#{@server.name}"
138
+ @server.clone("b-#{@server.name}", {:flags => LXC::LXC_CLONE_SNAPSHOT|LXC::LXC_CLONE_KEEPMACADDR})
139
+ end
140
+ end
141
+
142
+ def create_base_server
143
+ base_server = DevLXC::Container.new(@base_server_name)
144
+ if base_server.defined?
145
+ puts "Using existing container #{base_server.name}"
146
+ return base_server
147
+ end
148
+ base_platform = DevLXC.create_base_platform(@base_platform)
149
+ puts "Cloning container #{base_platform.name} into container #{base_server.name}"
150
+ base_platform.clone(base_server.name, {:flags => LXC::LXC_CLONE_SNAPSHOT})
151
+ base_server = DevLXC::Container.new(base_server.name)
152
+
153
+ # Rename procps in Ubuntu platforms because Enterprise Chef server < 11.0.0
154
+ # postgres recipe will use it even though it does not work in an LXC container
155
+ @packages["server"].to_s.match(/private-chef[_-](\d+)\.(\d+\.?){2,}-/)
156
+ if base_platform.name.include?("ubuntu") && Regexp.last_match[1].to_i < 11
157
+ FileUtils.mv("#{base_server.config_item('lxc.rootfs')}/etc/init.d/procps",
158
+ "#{base_server.config_item('lxc.rootfs')}/etc/init.d/procps.orig")
159
+ end
160
+ base_server.sync_mounts(@mounts)
161
+ base_server.start
162
+ base_server.install_package(@packages["server"]) unless @packages["server"].nil?
163
+ base_server.install_package(@packages["reporting"]) unless @packages["reporting"].nil?
164
+ base_server.install_package(@packages["push-jobs-server"]) unless @packages["push-jobs-server"].nil?
165
+ base_server.stop
166
+ return base_server
167
+ end
168
+
169
+ def configure_server
170
+ case @role
171
+ when "open-source"
172
+ puts "Creating /etc/chef-server/chef-server.rb"
173
+ FileUtils.mkdir("#{@server.config_item('lxc.rootfs')}/etc/chef-server")
174
+ IO.write("#{@server.config_item('lxc.rootfs')}/etc/chef-server/chef-server.rb", @chef_server_config)
175
+ run_ctl("chef-server", "reconfigure")
176
+ when "standalone", "bootstrap_backend"
177
+ puts "Creating /etc/opscode/private-chef.rb"
178
+ FileUtils.mkdir("#{@server.config_item('lxc.rootfs')}/etc/opscode")
179
+ IO.write("#{@server.config_item('lxc.rootfs')}/etc/opscode/private-chef.rb", @chef_server_config)
180
+ run_ctl("private-chef", "reconfigure")
181
+ when "secondary_backend", "frontend"
182
+ puts "Copying /etc/opscode from bootstrap backend"
183
+ FileUtils.cp_r("#{LXC::Container.new(@bootstrap_backend).config_item('lxc.rootfs')}/etc/opscode",
184
+ "#{@server.config_item('lxc.rootfs')}/etc")
185
+ run_ctl("private-chef", "reconfigure")
186
+ end
187
+ end
188
+
189
+ def configure_reporting
190
+ if %w(secondary_backend frontend).include?(@role)
191
+ puts "Copying /etc/opscode-reporting from bootstrap backend"
192
+ FileUtils.cp_r("#{LXC::Container.new(@bootstrap_backend).config_item('lxc.rootfs')}/etc/opscode-reporting",
193
+ "#{@server.config_item('lxc.rootfs')}/etc")
194
+ end
195
+ run_ctl("private-chef", "reconfigure")
196
+ run_ctl("opscode-reporting", "reconfigure")
197
+ end
198
+
199
+ def configure_push_jobs_server
200
+ run_ctl("opscode-push-jobs-server", "reconfigure")
201
+ if %w(bootstrap_backend secondary_backend).include?(@role)
202
+ run_ctl("private-chef", "reconfigure")
203
+ end
204
+ run_ctl("private-chef", "restart opscode-pushy-server")
205
+ end
206
+
207
+ def configure_manage
208
+ puts "Disabling old opscode-webui in /etc/opscode/private-chef.rb"
209
+ DevLXC.search_file_delete_line("#{@server.config_item('lxc.rootfs')}/etc/opscode/private-chef.rb", /opscode_webui[.enable.]/)
210
+ DevLXC.append_line_to_file("#{@server.config_item('lxc.rootfs')}/etc/opscode/private-chef.rb", "\nopscode_webui['enable'] = false\n")
211
+ run_ctl("private-chef", "reconfigure")
212
+ run_ctl("opscode-manage", "reconfigure")
213
+ end
214
+
215
+ def run_ctl(component, subcommand)
216
+ puts "Running `#{component}-ctl #{subcommand}` in #{@server.name}"
217
+ @server.run_command("#{component}-ctl #{subcommand}")
218
+ end
219
+
220
+ def create_users
221
+ puts "Creating users, keys and knife config files"
222
+ FileUtils.mkdir_p(["#{@server.config_item('lxc.rootfs')}/cookbooks/create_users/recipes",
223
+ "#{@server.config_item('lxc.rootfs')}/cookbooks/create_users/templates/default",
224
+ "#{@server.config_item('lxc.rootfs')}/cookbooks/create_users/libraries"])
225
+ FileUtils.cp("#{File.dirname(__FILE__)}/../../files/create_users/default.rb", "#{@server.config_item('lxc.rootfs')}/cookbooks/create_users/recipes")
226
+ DevLXC.search_file_replace("#{@server.config_item('lxc.rootfs')}/cookbooks/create_users/recipes/default.rb", /chef\.lxc/, @api_fqdn)
227
+ FileUtils.cp("#{File.dirname(__FILE__)}/../../files/create_users/knife.rb.erb", "#{@server.config_item('lxc.rootfs')}/cookbooks/create_users/templates/default")
228
+ FileUtils.cp("#{File.dirname(__FILE__)}/../../files/create_users/create_users.rb", "#{@server.config_item('lxc.rootfs')}/cookbooks/create_users/libraries")
229
+ IO.write("#{@server.config_item('lxc.rootfs')}/cookbooks/solo.rb", "cookbook_path '/cookbooks'")
230
+ @server.run_command("/opt/opscode/embedded/bin/chef-solo -c /cookbooks/solo.rb -o create_users -l info")
231
+ FileUtils.rm_r("#{@server.config_item('lxc.rootfs')}/cookbooks")
232
+ end
233
+ end
234
+ end