CloudyScripts 2.12.50 → 2.14.50
Sign up to get free protection for your applications and to get access to all the features.
- data/Rakefile +1 -1
- data/lib/help/remote_command_handler.rb +4 -2
- data/lib/help/state_transition_helper.rb +83 -8
- data/lib/scripts/ec2/ami2_ebs_conversion.rb +2 -1
- data/lib/scripts/ec2/copy_ami.rb +9 -2
- data/lib/scripts/ec2/copy_mswindows_ami.rb +68 -18
- data/lib/scripts/ec2/copy_mswindows_snapshot.rb +12 -7
- data/lib/scripts/ec2/copy_snapshot.rb +10 -2
- metadata +4 -4
data/Rakefile
CHANGED
@@ -12,7 +12,7 @@ require 'rake/testtask'
|
|
12
12
|
|
13
13
|
spec = Gem::Specification.new do |s|
|
14
14
|
s.name = 'CloudyScripts'
|
15
|
-
s.version = '2.
|
15
|
+
s.version = '2.14.50' #<number cloud-stacks supported>.<number cloud-scripts>.<counting releases>
|
16
16
|
s.has_rdoc = true
|
17
17
|
s.extra_rdoc_files = ['README.rdoc', 'LICENSE']
|
18
18
|
s.summary = 'Scripts to facilitate programming for infrastructure clouds.'
|
@@ -66,12 +66,14 @@ class RemoteCommandHandler
|
|
66
66
|
|
67
67
|
# Get root partition label
|
68
68
|
def get_root_device()
|
69
|
-
get_output("cat /etc/mtab | grep -E '[[:blank:]]+\/[[:blank:]]+' | cut -d ' ' -f 1").strip
|
69
|
+
#get_output("cat /etc/mtab | grep -E '[[:blank:]]+\/[[:blank:]]+' | cut -d ' ' -f 1").strip
|
70
|
+
get_output("mount | grep -E '[[:blank:]]+\/[[:blank:]]+' | cut -d ' ' -f 1").strip
|
70
71
|
end
|
71
72
|
|
72
73
|
# Get partition label
|
73
74
|
def get_partition_device(part)
|
74
|
-
get_output("cat /etc/mtab | grep -E '[[:blank:]]+" + "#{part}" + "[[:blank:]]+' | cut -d ' ' -f 1").strip
|
75
|
+
#get_output("cat /etc/mtab | grep -E '[[:blank:]]+" + "#{part}" + "[[:blank:]]+' | cut -d ' ' -f 1").strip
|
76
|
+
get_output("mount | grep -E '[[:blank:]]+" + "#{part}" + "[[:blank:]]+' | cut -d ' ' -f 1").strip
|
75
77
|
end
|
76
78
|
|
77
79
|
# Get device label
|
@@ -105,7 +105,7 @@ module StateTransitionHelper
|
|
105
105
|
# * kernel_id => EC2 Kernel ID of the started instance
|
106
106
|
# * ramdisk_id => EC2 Ramdisk ID of the started instance
|
107
107
|
# * architecture => architecture (e.g. 386i, 64x) of the started instance
|
108
|
-
def launch_instance(ami_id, key_name, security_group_name, ec2_handler = nil, type = nil)
|
108
|
+
def launch_instance(ami_id, key_name, security_group_name, ec2_handler = nil, type = nil, availability_zone = nil)
|
109
109
|
ec2_handler = ec2_handler() if ec2_handler == nil
|
110
110
|
post_message("starting up instance to execute the script (AMI = #{ami_id}) ...")
|
111
111
|
@logger.debug "start up AMI #{ami_id}"
|
@@ -124,7 +124,8 @@ module StateTransitionHelper
|
|
124
124
|
# now start it
|
125
125
|
res = ec2_handler.run_instances(:image_id => ami_id,
|
126
126
|
:security_group => security_group_name, :key_name => key_name,
|
127
|
-
:instance_type => instance_type
|
127
|
+
:instance_type => instance_type,
|
128
|
+
:availability_zone => availability_zone
|
128
129
|
)
|
129
130
|
instance_id = res['instancesSet']['item'][0]['instanceId']
|
130
131
|
@logger.info "started instance #{instance_id}"
|
@@ -230,6 +231,43 @@ module StateTransitionHelper
|
|
230
231
|
post_message("instance #{instance_id} is terminated")
|
231
232
|
end
|
232
233
|
|
234
|
+
# Stop an instance.
|
235
|
+
# Input Parameters:
|
236
|
+
# * instance_id => ID of the instance to be shut down
|
237
|
+
def stop_instance(instance_id, timeout = 240)
|
238
|
+
post_message("going to stop the temporary instance #{instance_id}...")
|
239
|
+
@logger.debug "stop instance #{instance_id}"
|
240
|
+
res = ec2_handler().stop_instances(:instance_id => instance_id)
|
241
|
+
done = false
|
242
|
+
while timeout > 0 && !done
|
243
|
+
res = ec2_handler().describe_instances(:instance_id => instance_id)
|
244
|
+
state = res['reservationSet']['item'][0]['instancesSet']['item'][0]['instanceState']
|
245
|
+
@logger.debug "instance in state '#{state['name']}' (#{state['code']})"
|
246
|
+
if state['code'].to_i == 80
|
247
|
+
done = true
|
248
|
+
timeout = 0
|
249
|
+
elsif state['code'].to_i != 64
|
250
|
+
done = false
|
251
|
+
timeout = 0
|
252
|
+
msg = "instance in state '#{state['name']}'"
|
253
|
+
@logger.error "#{msg}"
|
254
|
+
post_message("#{msg}")
|
255
|
+
end
|
256
|
+
sleep(5)
|
257
|
+
timeout -= 5
|
258
|
+
end
|
259
|
+
msg = ""
|
260
|
+
if !done
|
261
|
+
msg = "Failed to stop instance '#{instance_id}"
|
262
|
+
@logger.error "#{msg}"
|
263
|
+
raise Exception.new("Unable to stop instance '#{instance_id}'}")
|
264
|
+
else
|
265
|
+
msg = "'#{instance_id}' successfully stopped"
|
266
|
+
@logger.info "#{msg}"
|
267
|
+
end
|
268
|
+
post_message("#{msg}")
|
269
|
+
end
|
270
|
+
|
233
271
|
def retrieve_security_groups()
|
234
272
|
@context[:script].post_message("going to retrieve security groups...")
|
235
273
|
sgs = @context[:ec2_api_handler].describe_security_groups()
|
@@ -312,15 +350,15 @@ module StateTransitionHelper
|
|
312
350
|
# * volume_id => EC2 ID for the EBS Volume to be attached
|
313
351
|
# * instance_id => EC2 ID for the instance to which the volume is supposed to be attached to
|
314
352
|
# * temp_device_name => device name to be used for attaching (e.g. /dev/sdj1)
|
315
|
-
def attach_volume(volume_id, instance_id, temp_device_name)
|
353
|
+
def attach_volume(volume_id, instance_id, temp_device_name, timeout = 240)
|
316
354
|
post_message("going to attach volume #{volume_id} to instance #{instance_id} on device #{temp_device_name}...")
|
317
|
-
@logger.info "attach volume #{volume_id} to instance #{instance_id} on device #{temp_device_name}"
|
355
|
+
@logger.info "attach volume #{volume_id} to instance #{instance_id} on device #{temp_device_name} (using a timeout of #{timeout})s"
|
318
356
|
ec2_handler().attach_volume(:volume_id => volume_id,
|
319
357
|
:instance_id => instance_id,
|
320
358
|
:device => temp_device_name
|
321
359
|
)
|
322
360
|
done = false
|
323
|
-
timeout = 120
|
361
|
+
#timeout = 120
|
324
362
|
while timeout > 0
|
325
363
|
res = ec2_handler().describe_volumes(:volume_id => volume_id)
|
326
364
|
vol_state = res['volumeSet']['item'][0]['status']
|
@@ -352,14 +390,14 @@ module StateTransitionHelper
|
|
352
390
|
# Input Parameters:
|
353
391
|
# * volume_id => EC2 ID for the EBS Volume to be detached
|
354
392
|
# * instance_id => EC2 ID for the instance to detach from
|
355
|
-
def detach_volume(volume_id, instance_id)
|
393
|
+
def detach_volume(volume_id, instance_id, timeout = 240)
|
356
394
|
post_message("going to detach volume #{volume_id} from instance #{instance_id}...")
|
357
|
-
@logger.info "detach volume #{volume_id} from instance #{instance_id}"
|
395
|
+
@logger.info "detach volume #{volume_id} from instance #{instance_id} (using a timeout of #{timeout})s"
|
358
396
|
ec2_handler().detach_volume(:volume_id => volume_id,
|
359
397
|
:instance_id => instance_id
|
360
398
|
)
|
361
399
|
done = false
|
362
|
-
timeout = 120
|
400
|
+
#timeout = 120
|
363
401
|
while timeout > 0
|
364
402
|
sleep(3)
|
365
403
|
res = ec2_handler().describe_volumes(:volume_id => volume_id)
|
@@ -428,6 +466,26 @@ module StateTransitionHelper
|
|
428
466
|
post_message("snapshot #{snapshot_id} deleted")
|
429
467
|
end
|
430
468
|
|
469
|
+
# Is Snapshot accessible?
|
470
|
+
def snapshot_accessible(snapshot_id)
|
471
|
+
post_message("checking snapshot '#{snapshot_id}' accessibility...")
|
472
|
+
@logger.info("checking snapshot '#{snapshot_id}' accessibility...")
|
473
|
+
begin
|
474
|
+
ec2_handler().describe_snapshots(:snapshot_id => snapshot_id)
|
475
|
+
rescue Exception => e
|
476
|
+
if e.to_str =~ /does not exist/ && e.to_str =~ /#{snapshot_id}/
|
477
|
+
post_message("'#{snapshot_id}' NOT accessible")
|
478
|
+
@logger.info("'#{snapshot_id}' NOT accessible")
|
479
|
+
return false
|
480
|
+
else
|
481
|
+
raise e
|
482
|
+
end
|
483
|
+
end
|
484
|
+
post_message("'#{snapshot_id}' accessible")
|
485
|
+
@logger.info("'#{snapshot_id}' accessible")
|
486
|
+
return true
|
487
|
+
end
|
488
|
+
|
431
489
|
# Registers a snapshot as EBS-booted AMI.
|
432
490
|
# Input Parameters:
|
433
491
|
# * snapshot_id => EC2 Snapshot ID used to be used
|
@@ -733,6 +791,23 @@ module StateTransitionHelper
|
|
733
791
|
return part_fs_type, part_label
|
734
792
|
end
|
735
793
|
|
794
|
+
# Retrieve the root volume ID of an instance
|
795
|
+
def get_root_volume_id(instance_id)
|
796
|
+
post_message("getting 'root volume ID' (volume ID attached as RootDeviceName) of '#{instance_id}' instance...")
|
797
|
+
volume_id = nil
|
798
|
+
res = ec2_handler().describe_instances(:instance_id => instance_id)
|
799
|
+
root_device_name = res['reservationSet']['item'][0]['instancesSet']['item'][0]['rootDeviceName']
|
800
|
+
block_device_map = res['reservationSet']['item'][0]['instancesSet']['item'][0]['blockDeviceMapping']['item']
|
801
|
+
block_device_map.each(){|blk_dev|
|
802
|
+
if blk_dev['deviceName'] == root_device_name
|
803
|
+
volume_id = blk_dev['ebs']['volumeId']
|
804
|
+
post_message("found '#{volume_id}' attached as '#{root_device_name}' rootDeviceName")
|
805
|
+
break
|
806
|
+
end
|
807
|
+
}
|
808
|
+
return volume_id
|
809
|
+
end
|
810
|
+
|
736
811
|
# Copy all files of a running linux distribution via rsync to a mounted directory
|
737
812
|
# Input Parameters:
|
738
813
|
# * destination_path => where to copy to
|
@@ -84,6 +84,7 @@ class Ami2EbsConversion < Ec2Script
|
|
84
84
|
# which serves to create
|
85
85
|
class InitialState < Ami2EbsConversionState
|
86
86
|
def enter
|
87
|
+
puts "DEBUG: params: #{@context[:ami_id]}, #{@context[:key_name]}, #{@context[:security_group_name]}"
|
87
88
|
@context[:instance_id], @context[:dns_name], @context[:availability_zone],
|
88
89
|
@context[:kernel_id], @context[:ramdisk_id], @context[:architecture] =
|
89
90
|
launch_instance(@context[:ami_id], @context[:key_name], @context[:security_group_name])
|
@@ -107,7 +108,7 @@ class Ami2EbsConversion < Ec2Script
|
|
107
108
|
end
|
108
109
|
end
|
109
110
|
|
110
|
-
# Storage attached. Create a file-system and
|
111
|
+
# Storage attached. Create a file-system and mount it
|
111
112
|
class StorageAttached < Ami2EbsConversionState
|
112
113
|
def enter
|
113
114
|
@context[:result][:os] =
|
data/lib/scripts/ec2/copy_ami.rb
CHANGED
@@ -189,8 +189,12 @@ class CopyAmi < Ec2Script
|
|
189
189
|
path_candidates = ["/#{@context[:source_ssh_username]}/.ssh/",
|
190
190
|
"/home/#{@context[:source_ssh_username]}/.ssh/"]
|
191
191
|
key_path = determine_file(@context[:source_dns_name], @context[:source_ssh_username], @context[:source_ssh_keydata], path_candidates)
|
192
|
+
#XXX: fix the problem fo key name with white space
|
193
|
+
#upload_file(@context[:source_dns_name], @context[:source_ssh_username], @context[:source_ssh_keydata],
|
194
|
+
# @context[:target_ssh_keyfile], "#{key_path}#{@context[:target_key_name]}.pem")
|
192
195
|
upload_file(@context[:source_dns_name], @context[:source_ssh_username], @context[:source_ssh_keydata],
|
193
|
-
@context[:target_ssh_keyfile], "#{key_path}#{@context[:target_key_name]}.pem")
|
196
|
+
@context[:target_ssh_keyfile], "#{key_path}#{@context[:target_key_name].gsub(/\s+/, '_')}.pem")
|
197
|
+
|
194
198
|
post_message("credentials are in place to connect source and target.")
|
195
199
|
KeyInPlaceState.new(@context)
|
196
200
|
end
|
@@ -206,7 +210,10 @@ class CopyAmi < Ec2Script
|
|
206
210
|
connect(@context[:source_dns_name], @context[:source_ssh_username], nil, @context[:source_ssh_keydata])
|
207
211
|
source_dir = "/mnt/tmp_#{@context[:source_volume_id]}/"
|
208
212
|
dest_dir = "/mnt/tmp_#{@context[:target_volume_id]}"
|
209
|
-
|
213
|
+
#XXX: fix the problem fo key name with white space
|
214
|
+
#remote_copy(@context[:source_ssh_username], @context[:target_key_name], source_dir,
|
215
|
+
# @context[:target_dns_name], @context[:target_ssh_username], dest_dir)
|
216
|
+
remote_copy(@context[:source_ssh_username], @context[:target_key_name].gsub(/\s+/, '_'), source_dir,
|
210
217
|
@context[:target_dns_name], @context[:target_ssh_username], dest_dir)
|
211
218
|
disconnect()
|
212
219
|
#
|
@@ -54,11 +54,11 @@ class CopyMsWindowsAmi < Ec2Script
|
|
54
54
|
if @input_params[:helper_ami_id] == nil && !(@input_params[:helper_ami_id] =~ /^ami-.*$/)
|
55
55
|
raise Exception.new("Invalid Helper AMI ID specified: #{@input_params[:helper_ami_id]}")
|
56
56
|
end
|
57
|
-
if @
|
57
|
+
if @remote_ec2_helper.ami_prop(@input_params[:helper_ami_id], 'rootDeviceType') != "ebs"
|
58
58
|
raise Exception.new("must be an EBS type image")
|
59
59
|
end
|
60
|
-
if @
|
61
|
-
raise Exception.new("Not a MS Windows AMI: #{@
|
60
|
+
if @remote_ec2_helper.ami_prop(@input_params[:helper_ami_id], 'platform') != "windows"
|
61
|
+
raise Exception.new("Not a MS Windows AMI: #{@remote_ec2_helper.ami_prop(@input_params[:helper_ami_id], 'platform')}")
|
62
62
|
end
|
63
63
|
# AWS Linux AMI, source and target region
|
64
64
|
if @input_params[:source_ami_id] == nil && !(@input_params[:source_ami_id] =~ /^ami-.*$/)
|
@@ -138,6 +138,7 @@ class CopyMsWindowsAmi < Ec2Script
|
|
138
138
|
# - Volume size from this AMI
|
139
139
|
# - Availability Zone
|
140
140
|
#NB: less modification if we get the AZ from the launched instance
|
141
|
+
#NB: if we do not own this AMI, we have no snapshot, so we must launch an instance
|
141
142
|
class InitialState < CopyMsWindowsAmiState
|
142
143
|
def enter()
|
143
144
|
local_region()
|
@@ -149,13 +150,37 @@ class CopyMsWindowsAmi < Ec2Script
|
|
149
150
|
#puts "Setting Source and Target Availability Zone if not set"
|
150
151
|
#@context[:source_availability_zone] = "us-east-1a" unless @context[:source_availability_zone] != nil
|
151
152
|
#@context[:target_availability_zone] = "us-west-1a" unless @context[:target_availability_zone] != nil
|
152
|
-
|
153
|
+
|
154
|
+
#try to access snapshot, if not possible, launch and stop an AMI to create one
|
155
|
+
if !snapshot_accessible(@context[:snapshot_id])
|
156
|
+
puts "The AMI's snapshot is NOT accessible, we must launch an instance to create one"
|
157
|
+
|
158
|
+
end
|
153
159
|
|
154
160
|
#raise Exception.new("DEBUG: FORCED Script exit")
|
155
161
|
InitialStateDone.new(@context)
|
156
162
|
end
|
157
163
|
end
|
158
164
|
|
165
|
+
# Consitionnal State (launching an instance and creating a snapshot)
|
166
|
+
class InitialStateLaunch < CopyMsWindowsAmiState
|
167
|
+
def enter()
|
168
|
+
local_region()
|
169
|
+
puts "Launching and stopping an instance of the AMI to create a snapshot"
|
170
|
+
result = launch_instance(@context[:ami_id], @context[:source_key_name], @context[:source_security_groups])
|
171
|
+
instance_id = result.first
|
172
|
+
puts "Instance launched with ID: #{instance_id}"
|
173
|
+
puts "Waiting 3 minutes before stopping instance '#{instance_id}' for creating a Snapshot of the rootDevice"
|
174
|
+
sleep(180)
|
175
|
+
stop_instance(instance_id)
|
176
|
+
puts "Instance '#{instance_id}' stopped, creating snapshot"
|
177
|
+
ebs_volume_id = ec2_helper.get_attached_volumes(instance_id)[0]['volumeId']
|
178
|
+
@context[:snapshot_id] = create_snapshot(ebs_volume_id, "Cloudy_Scripts Snapshot for copying AMIs")
|
179
|
+
|
180
|
+
InitialStateDone.new(@context)
|
181
|
+
end
|
182
|
+
end
|
183
|
+
|
159
184
|
# Initial state: Launch an Amazon Linux AMI in the source Region
|
160
185
|
class InitialStateDone < CopyMsWindowsAmiState
|
161
186
|
def enter()
|
@@ -318,11 +343,14 @@ class CopyMsWindowsAmi < Ec2Script
|
|
318
343
|
# a remote copy.
|
319
344
|
class TargetVolumeReadyState < CopyMsWindowsAmiState
|
320
345
|
def enter()
|
321
|
-
post_message("
|
346
|
+
post_message("Uploading key of target-instance to source-instance...")
|
322
347
|
path_candidates = ["/#{@context[:source_ssh_username]}/.ssh/", "/home/#{@context[:source_ssh_username]}/.ssh/"]
|
323
348
|
key_path = determine_file(@context[:source_dns_name], @context[:source_ssh_username], @context[:source_ssh_keydata], path_candidates)
|
349
|
+
#XXX: fix the problem fo key name with white space
|
350
|
+
#upload_file(@context[:source_dns_name], @context[:source_ssh_username], @context[:source_ssh_keydata],
|
351
|
+
# @context[:target_ssh_keyfile], "#{key_path}#{@context[:target_key_name]}.pem")
|
324
352
|
upload_file(@context[:source_dns_name], @context[:source_ssh_username], @context[:source_ssh_keydata],
|
325
|
-
@context[:target_ssh_keyfile], "#{key_path}#{@context[:target_key_name]}.pem")
|
353
|
+
@context[:target_ssh_keyfile], "#{key_path}#{@context[:target_key_name].gsub(/\s+/, '_')}.pem")
|
326
354
|
post_message("credentials are in place to connect source and target (from source to target).")
|
327
355
|
|
328
356
|
KeyInPlaceState.new(@context)
|
@@ -332,14 +360,18 @@ class CopyMsWindowsAmi < Ec2Script
|
|
332
360
|
# Now we can copy.
|
333
361
|
class KeyInPlaceState < CopyMsWindowsAmiState
|
334
362
|
def enter()
|
363
|
+
post_message("Transfering archive from Source to Target Region...")
|
335
364
|
connect(@context[:target_dns_name], @context[:target_ssh_username], nil, @context[:target_ssh_keydata])
|
336
365
|
disable_ssh_tty(@context[:target_dns_name])
|
337
366
|
disconnect()
|
338
367
|
#
|
339
368
|
connect(@context[:source_dns_name], @context[:source_ssh_username], nil, @context[:source_ssh_keydata])
|
340
|
-
source_dir = "/mnt/tmp_#{@context[:source_temp_volume_id]}"
|
341
|
-
dest_dir = "/mnt/tmp_#{@context[:target_temp_volume_id]}"
|
342
|
-
|
369
|
+
source_dir = "/mnt/tmp_#{@context[:source_temp_volume_id]}/"
|
370
|
+
dest_dir = "/mnt/tmp_#{@context[:target_temp_volume_id]}/"
|
371
|
+
#XXX: fix the problem fo key name with white space
|
372
|
+
#remote_copy(@context[:source_ssh_username], @context[:target_key_name], source_dir,
|
373
|
+
# @context[:target_dns_name], @context[:target_ssh_username], dest_dir)
|
374
|
+
remote_copy(@context[:source_ssh_username], @context[:target_key_name].gsub(/\s+/, '_'), source_dir,
|
343
375
|
@context[:target_dns_name], @context[:target_ssh_username], dest_dir)
|
344
376
|
disconnect()
|
345
377
|
#
|
@@ -354,6 +386,7 @@ class CopyMsWindowsAmi < Ec2Script
|
|
354
386
|
# Decompress data on the device
|
355
387
|
class DataCopiedState < CopyMsWindowsAmiState
|
356
388
|
def enter()
|
389
|
+
post_message("Dumping transfered archive to volume...")
|
357
390
|
remote_region()
|
358
391
|
connect(@context[:target_dns_name], @context[:target_ssh_username], nil, @context[:target_ssh_keydata])
|
359
392
|
mount_point = "/mnt/tmp_#{@context[:target_temp_volume_id]}"
|
@@ -371,11 +404,10 @@ class CopyMsWindowsAmi < Ec2Script
|
|
371
404
|
#XXX: TODO
|
372
405
|
class RestoredDataState < CopyMsWindowsAmiState
|
373
406
|
def enter()
|
407
|
+
post_message("Detaching migrated volume...")
|
374
408
|
remote_region()
|
375
409
|
detach_volume(@context[:target_volume_id], @context[:target_instance_id])
|
376
410
|
|
377
|
-
#@context[:new_snapshot_id] = create_snapshot(@context[:target_volume_id], "Created by CloudyScripts - copy_mswindows_ami")
|
378
|
-
|
379
411
|
TargetVolumeCreatedState.new(@context)
|
380
412
|
end
|
381
413
|
end
|
@@ -385,21 +417,38 @@ class CopyMsWindowsAmi < Ec2Script
|
|
385
417
|
# - launch same AMI as the one we want to copy and stop it (after it has boot up): use helper_ami_id
|
386
418
|
# - detach the volume of this instance and attach the new volume
|
387
419
|
# - start the instance to see if everything is good, then stop it
|
388
|
-
# - create an
|
420
|
+
# - create an AMI from this instance
|
389
421
|
class TargetVolumeCreatedState < CopyMsWindowsAmiState
|
390
422
|
def enter()
|
423
|
+
post_message("Launching Helper AMI '#{@context[:helper_ami_id]}' for attaching migrated volume...")
|
391
424
|
remote_region()
|
392
425
|
#XXX: launch instance in the right AZ
|
393
|
-
result = launch_instance(@context[:helper_ami_id], @context[:target_key_name], @context[:target_security_groups]
|
394
|
-
|
426
|
+
result = launch_instance(@context[:helper_ami_id], @context[:target_key_name], @context[:target_security_groups],
|
427
|
+
nil, nil, @context[:target_availability_zone])
|
428
|
+
@context[:helper_instance_id] = result.first
|
395
429
|
@context[:helper_dns_name] = result[1]
|
396
430
|
@context[:helper_availability_zone] = result[2]
|
397
|
-
@context[:
|
431
|
+
@context[:helper_root_device_name] = result[6]
|
398
432
|
|
399
433
|
#XXX:
|
400
434
|
# - wait for it to be running, and then stop it
|
401
|
-
# - wait for it to be stopped, and then
|
402
|
-
|
435
|
+
# - wait for it to be stopped, and then start it with the new volume
|
436
|
+
stop_instance(@context[:helper_instance_id])
|
437
|
+
root_volume_id = get_root_volume_id(@context[:helper_instance_id])
|
438
|
+
detach_volume(root_volume_id, @context[:helper_instance_id])
|
439
|
+
attach_volume(@context[:target_volume_id], @context[:helper_instance_id], @context[:helper_root_device_name])
|
440
|
+
start_instance(@context[:helper_instance_id])
|
441
|
+
|
442
|
+
#XXX: return running instance for now
|
443
|
+
@context[:result][:instance_id] = result.first
|
444
|
+
|
445
|
+
#XXX: stop this instance
|
446
|
+
stop_instance(@context[:helper_instance_id])
|
447
|
+
|
448
|
+
#XXX: register as AMI
|
449
|
+
new_ami_id = create_image(:instance_id => @context[:helper_instance_id],
|
450
|
+
:name => @context[:name], :description => @context[:description])
|
451
|
+
@context[:result][:image_id] = new_ami_id
|
403
452
|
|
404
453
|
AmiRegisteredState.new(@context)
|
405
454
|
end
|
@@ -421,6 +470,7 @@ class CopyMsWindowsAmi < Ec2Script
|
|
421
470
|
# - delete source and temp volume
|
422
471
|
class AmiRegisteredState < CopyMsWindowsAmiState
|
423
472
|
def enter()
|
473
|
+
post_message("Cleaning Source and Target Regions...")
|
424
474
|
local_region()
|
425
475
|
connect(@context[:source_dns_name], @context[:source_ssh_username], nil, @context[:source_ssh_keydata])
|
426
476
|
mount_point = "/mnt/tmp_#{@context[:source_temp_volume_id]}"
|
@@ -440,7 +490,7 @@ class CopyMsWindowsAmi < Ec2Script
|
|
440
490
|
detach_volume(@context[:target_temp_volume_id], @context[:target_instance_id])
|
441
491
|
shut_down_instance(@context[:target_instance_id])
|
442
492
|
delete_volume(@context[:target_temp_volume_id])
|
443
|
-
delete_volume(@context[:target_volume_id])
|
493
|
+
#delete_volume(@context[:target_volume_id])
|
444
494
|
|
445
495
|
Done.new(@context)
|
446
496
|
end
|
@@ -296,8 +296,11 @@ class CopyMsWindowsSnapshot < Ec2Script
|
|
296
296
|
post_message("upload key of target-instance to source-instance...")
|
297
297
|
path_candidates = ["/#{@context[:source_ssh_username]}/.ssh/", "/home/#{@context[:source_ssh_username]}/.ssh/"]
|
298
298
|
key_path = determine_file(@context[:source_dns_name], @context[:source_ssh_username], @context[:source_ssh_keydata], path_candidates)
|
299
|
+
#XXX: fix the problem fo key name with white space
|
300
|
+
#upload_file(@context[:source_dns_name], @context[:source_ssh_username], @context[:source_ssh_keydata],
|
301
|
+
# @context[:target_ssh_keyfile], "#{key_path}#{@context[:target_key_name]}.pem")
|
299
302
|
upload_file(@context[:source_dns_name], @context[:source_ssh_username], @context[:source_ssh_keydata],
|
300
|
-
@context[:target_ssh_keyfile], "#{key_path}#{@context[:target_key_name]}.pem")
|
303
|
+
@context[:target_ssh_keyfile], "#{key_path}#{@context[:target_key_name].gsub(/\s+/, '_')}.pem")
|
301
304
|
post_message("credentials are in place to connect source and target (from source to target).")
|
302
305
|
|
303
306
|
KeyInPlaceState.new(@context)
|
@@ -312,10 +315,14 @@ class CopyMsWindowsSnapshot < Ec2Script
|
|
312
315
|
disconnect()
|
313
316
|
#
|
314
317
|
connect(@context[:source_dns_name], @context[:source_ssh_username], nil, @context[:source_ssh_keydata])
|
315
|
-
source_dir = "/mnt/tmp_#{@context[:source_temp_volume_id]}"
|
316
|
-
dest_dir = "/mnt/tmp_#{@context[:target_temp_volume_id]}"
|
317
|
-
|
318
|
+
source_dir = "/mnt/tmp_#{@context[:source_temp_volume_id]}/"
|
319
|
+
dest_dir = "/mnt/tmp_#{@context[:target_temp_volume_id]}/"
|
320
|
+
#XXX: fix the problem fo key name with white space
|
321
|
+
#remote_copy(@context[:source_ssh_username], @context[:target_key_name], source_dir,
|
322
|
+
# @context[:target_dns_name], @context[:target_ssh_username], dest_dir)
|
323
|
+
remote_copy(@context[:source_ssh_username], @context[:target_key_name].gsub(/\s+/, '_'), source_dir,
|
318
324
|
@context[:target_dns_name], @context[:target_ssh_username], dest_dir)
|
325
|
+
|
319
326
|
disconnect()
|
320
327
|
#
|
321
328
|
connect(@context[:target_dns_name], @context[:target_ssh_username], nil, @context[:target_ssh_keydata])
|
@@ -351,9 +358,7 @@ class CopyMsWindowsSnapshot < Ec2Script
|
|
351
358
|
@context[:new_snapshot_id] = create_snapshot(@context[:target_volume_id], "Created by CloudyScripts - copy_mswindows_ami")
|
352
359
|
@context[:result][:snapshot_id] = @context[:new_snapshot_id]
|
353
360
|
|
354
|
-
|
355
|
-
Done.new(@context)
|
356
|
-
#TargetSnapshotCreatedState.new(@context)
|
361
|
+
TargetSnapshotCreatedState.new(@context)
|
357
362
|
end
|
358
363
|
end
|
359
364
|
|
@@ -149,8 +149,12 @@ class CopySnapshot< Ec2Script
|
|
149
149
|
key_path = determine_file(@context[:source_dns_name], @context[:source_ssh_username], @context[:source_ssh_keydata], path_candidates)
|
150
150
|
#upload_file(@context[:source_dns_name], "root", @context[:source_ssh_keydata],
|
151
151
|
# @context[:target_ssh_keyfile], "#{key_path}#{@context[:target_key_name]}.pem")
|
152
|
+
#XXX: fix the problem fo key name with white space
|
153
|
+
#upload_file(@context[:source_dns_name], @context[:source_ssh_username], @context[:source_ssh_keydata],
|
154
|
+
# @context[:target_ssh_keyfile], "#{key_path}#{@context[:target_key_name]}.pem")
|
152
155
|
upload_file(@context[:source_dns_name], @context[:source_ssh_username], @context[:source_ssh_keydata],
|
153
|
-
@context[:target_ssh_keyfile], "#{key_path}#{@context[:target_key_name]}.pem")
|
156
|
+
@context[:target_ssh_keyfile], "#{key_path}#{@context[:target_key_name].gsub(/\s+/, '_')}.pem")
|
157
|
+
|
154
158
|
post_message("credentials are in place to connect source and target.")
|
155
159
|
KeyInPlaceState.new(@context)
|
156
160
|
end
|
@@ -166,8 +170,12 @@ class CopySnapshot< Ec2Script
|
|
166
170
|
connect(@context[:source_dns_name], @context[:source_ssh_username], nil, @context[:source_ssh_keydata])
|
167
171
|
source_dir = "/mnt/tmp_#{@context[:source_volume_id]}/"
|
168
172
|
dest_dir = "/mnt/tmp_#{@context[:target_volume_id]}"
|
169
|
-
|
173
|
+
#XXX: fix the problem fo key name with white space
|
174
|
+
#remote_copy(@context[:source_ssh_username], @context[:target_key_name], source_dir,
|
175
|
+
# @context[:target_dns_name], @context[:target_ssh_username], dest_dir)
|
176
|
+
remote_copy(@context[:source_ssh_username], @context[:target_key_name].gsub(/\s+/, '_'), source_dir,
|
170
177
|
@context[:target_dns_name], @context[:target_ssh_username], dest_dir)
|
178
|
+
|
171
179
|
disconnect()
|
172
180
|
#
|
173
181
|
connect(@context[:target_dns_name], @context[:target_ssh_username], nil, @context[:target_ssh_keydata])
|
metadata
CHANGED
@@ -1,13 +1,13 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: CloudyScripts
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
hash:
|
4
|
+
hash: 83
|
5
5
|
prerelease: false
|
6
6
|
segments:
|
7
7
|
- 2
|
8
|
-
-
|
8
|
+
- 14
|
9
9
|
- 50
|
10
|
-
version: 2.
|
10
|
+
version: 2.14.50
|
11
11
|
platform: ruby
|
12
12
|
authors:
|
13
13
|
- Matthias Jung
|
@@ -15,7 +15,7 @@ autorequire:
|
|
15
15
|
bindir: bin
|
16
16
|
cert_chain: []
|
17
17
|
|
18
|
-
date:
|
18
|
+
date: 2012-01-03 00:00:00 +00:00
|
19
19
|
default_executable:
|
20
20
|
dependencies:
|
21
21
|
- !ruby/object:Gem::Dependency
|