solutious-rudy 0.4.0 → 0.5.0
Sign up to get free protection for your applications and to get access to all the features.
- data/CHANGES.txt +8 -9
- data/README.rdoc +48 -7
- data/Rakefile +102 -7
- data/Rudyfile +28 -0
- data/bin/ird +162 -0
- data/bin/rudy +287 -93
- data/lib/annoy.rb +227 -0
- data/lib/aws_sdb/service.rb +1 -1
- data/lib/console.rb +20 -4
- data/lib/escape.rb +305 -0
- data/lib/rudy.rb +265 -125
- data/lib/rudy/aws.rb +61 -26
- data/lib/rudy/aws/ec2.rb +20 -296
- data/lib/rudy/aws/ec2/address.rb +121 -0
- data/lib/rudy/aws/ec2/group.rb +241 -0
- data/lib/rudy/aws/ec2/image.rb +46 -0
- data/lib/rudy/aws/ec2/instance.rb +407 -0
- data/lib/rudy/aws/ec2/keypair.rb +92 -0
- data/lib/rudy/aws/ec2/snapshot.rb +87 -0
- data/lib/rudy/aws/ec2/volume.rb +234 -0
- data/lib/rudy/aws/simpledb.rb +33 -15
- data/lib/rudy/cli.rb +142 -0
- data/lib/rudy/cli/addresses.rb +85 -0
- data/lib/rudy/cli/backups.rb +175 -0
- data/lib/rudy/{command → cli}/config.rb +18 -13
- data/lib/rudy/cli/deploy.rb +12 -0
- data/lib/rudy/cli/disks.rb +125 -0
- data/lib/rudy/cli/domains.rb +17 -0
- data/lib/rudy/cli/groups.rb +77 -0
- data/lib/rudy/{command → cli}/images.rb +18 -6
- data/lib/rudy/cli/instances.rb +142 -0
- data/lib/rudy/cli/keypairs.rb +47 -0
- data/lib/rudy/cli/manager.rb +51 -0
- data/lib/rudy/{command → cli}/release.rb +10 -10
- data/lib/rudy/cli/routines.rb +80 -0
- data/lib/rudy/cli/volumes.rb +121 -0
- data/lib/rudy/command/addresses.rb +62 -39
- data/lib/rudy/command/backups.rb +60 -170
- data/lib/rudy/command/disks-old.rb +322 -0
- data/lib/rudy/command/disks.rb +5 -209
- data/lib/rudy/command/domains.rb +34 -0
- data/lib/rudy/command/groups.rb +105 -48
- data/lib/rudy/command/instances.rb +263 -70
- data/lib/rudy/command/keypairs.rb +149 -0
- data/lib/rudy/command/manager.rb +65 -0
- data/lib/rudy/command/volumes.rb +110 -49
- data/lib/rudy/config.rb +90 -70
- data/lib/rudy/config/objects.rb +67 -0
- data/lib/rudy/huxtable.rb +253 -0
- data/lib/rudy/metadata/backup.rb +23 -48
- data/lib/rudy/metadata/disk.rb +79 -68
- data/lib/rudy/metadata/machine.rb +34 -0
- data/lib/rudy/routines.rb +54 -0
- data/lib/rudy/routines/disk_handler.rb +190 -0
- data/lib/rudy/routines/release.rb +15 -0
- data/lib/rudy/routines/script_runner.rb +65 -0
- data/lib/rudy/routines/shutdown.rb +42 -0
- data/lib/rudy/routines/startup.rb +48 -0
- data/lib/rudy/utils.rb +57 -2
- data/lib/storable.rb +11 -5
- data/lib/sysinfo.rb +274 -0
- data/rudy.gemspec +84 -20
- data/support/randomize-root-password +45 -0
- data/support/rudy-ec2-startup +5 -5
- data/support/update-ec2-ami-tools +20 -0
- data/test/05_config/00_setup_test.rb +24 -0
- data/test/05_config/30_machines_test.rb +69 -0
- data/test/20_sdb/00_setup_test.rb +31 -0
- data/test/20_sdb/10_domains_test.rb +113 -0
- data/test/25_ec2/00_setup_test.rb +34 -0
- data/test/25_ec2/10_keypairs_test.rb +33 -0
- data/test/25_ec2/20_groups_test.rb +139 -0
- data/test/25_ec2/30_addresses_test.rb +35 -0
- data/test/25_ec2/40_volumes_test.rb +46 -0
- data/test/25_ec2/50_snapshots_test.rb +69 -0
- data/test/26_ec2_instances/00_setup_test.rb +33 -0
- data/test/26_ec2_instances/10_instances_test.rb +81 -0
- data/test/26_ec2_instances/50_images_test.rb +13 -0
- data/test/30_sdb_metadata/00_setup_test.rb +28 -0
- data/test/30_sdb_metadata/10_disks_test.rb +99 -0
- data/test/30_sdb_metadata/20_backups_test.rb +102 -0
- data/test/50_commands/00_setup_test.rb +11 -0
- data/test/50_commands/10_keypairs_test.rb +79 -0
- data/test/50_commands/20_groups_test.rb +77 -0
- data/test/50_commands/40_volumes_test.rb +55 -0
- data/test/50_commands/50_instances_test.rb +110 -0
- data/test/coverage.txt +51 -0
- data/test/helper.rb +35 -0
- data/tryouts/disks.rb +55 -0
- data/tryouts/nested_methods.rb +36 -0
- data/tryouts/session_tryout.rb +48 -0
- metadata +94 -25
- data/bin/rudy-ec2 +0 -108
- data/lib/rudy/command/base.rb +0 -839
- data/lib/rudy/command/deploy.rb +0 -12
- data/lib/rudy/command/environment.rb +0 -74
- data/lib/rudy/command/machines.rb +0 -170
- data/lib/rudy/command/metadata.rb +0 -41
- data/lib/rudy/metadata.rb +0 -26
data/lib/rudy/aws.rb
CHANGED
@@ -1,39 +1,63 @@
|
|
1
1
|
|
2
2
|
|
3
|
-
|
3
|
+
require 'EC2'
|
4
|
+
require 'aws_sdb'
|
4
5
|
|
5
6
|
module Rudy
|
6
7
|
module AWS
|
7
|
-
|
8
|
+
extend self
|
9
|
+
@@ec2 = @@sdb = @@s3 = nil
|
10
|
+
|
11
|
+
|
12
|
+
def ec2; @@ec2; end
|
13
|
+
def sdb; @@sdb; end
|
14
|
+
def s3; @@s3; end
|
15
|
+
|
16
|
+
def set_access_identifiers(accesskey, secretkey, logger=nil)
|
17
|
+
@@ec2 ||= Rudy::AWS::EC2.new(accesskey, secretkey)
|
18
|
+
@@sdb ||= Rudy::AWS::SimpleDB.new(accesskey, secretkey)
|
19
|
+
#@@s3 ||= Rudy::AWS::S3.new(accesskey, secretkey)
|
20
|
+
end
|
21
|
+
|
8
22
|
module ObjectBase
|
9
23
|
attr_accessor :aws
|
10
24
|
def initialize(aws_connection)
|
11
25
|
@aws = aws_connection
|
12
26
|
end
|
13
|
-
|
14
|
-
|
15
|
-
|
16
|
-
@@logger = StringIO.new
|
17
|
-
|
18
|
-
attr_reader :instances
|
19
|
-
attr_reader :images
|
20
|
-
attr_reader :addresses
|
21
|
-
attr_reader :groups
|
22
|
-
attr_reader :volumes
|
23
|
-
attr_reader :snapshots
|
24
|
-
attr_reader :aws
|
27
|
+
|
28
|
+
|
29
|
+
protected
|
25
30
|
|
26
|
-
|
27
|
-
|
28
|
-
|
29
|
-
|
30
|
-
|
31
|
-
|
32
|
-
|
33
|
-
|
31
|
+
# Execute AWS requests safely. This will trap errors and return
|
32
|
+
# a default value (if specified).
|
33
|
+
# * +default+ A default response value
|
34
|
+
# * +request+ A block which contains the AWS request
|
35
|
+
# Returns the return value from the request is returned untouched
|
36
|
+
# or the default value on error or if the request returned nil.
|
37
|
+
def execute_request(default=nil, timeout=nil, &request)
|
38
|
+
timeout ||= 30
|
39
|
+
raise "No block provided" unless request
|
40
|
+
response = nil
|
41
|
+
begin
|
42
|
+
Timeout::timeout(timeout) do
|
43
|
+
response = request.call
|
44
|
+
end
|
45
|
+
rescue ::EC2::Error => ex
|
46
|
+
STDERR.puts ex.message
|
47
|
+
rescue ::EC2::InvalidInstanceIDMalformed => ex
|
48
|
+
STDERR.puts ex.message
|
49
|
+
rescue Timeout::Error => ex
|
50
|
+
STDERR.puts "Timeout (#{timeout}): #{ex.message}!"
|
51
|
+
rescue SocketError => ex
|
52
|
+
STDERR.puts "Socket Error. Check your Internets!"
|
53
|
+
ensure
|
54
|
+
response ||= default
|
55
|
+
end
|
56
|
+
response
|
34
57
|
end
|
35
|
-
|
36
58
|
end
|
59
|
+
|
60
|
+
|
37
61
|
|
38
62
|
class S3
|
39
63
|
@@logger = StringIO.new
|
@@ -41,7 +65,7 @@ module Rudy
|
|
41
65
|
attr_reader :aws
|
42
66
|
|
43
67
|
def initialize(access_key, secret_key)
|
44
|
-
|
68
|
+
# @aws = RightAws::S3.new(access_key, secret_key, {:logger => Logger.new(@@logger)})
|
45
69
|
end
|
46
70
|
end
|
47
71
|
|
@@ -52,8 +76,7 @@ module Rudy
|
|
52
76
|
attr_reader :aws
|
53
77
|
|
54
78
|
def initialize(access_key, secret_key)
|
55
|
-
@aws =
|
56
|
-
@aws2 = AwsSdb::Service.new(:access_key_id => access_key, :secret_access_key => secret_key, :logger => Logger.new(@@logger))
|
79
|
+
@aws = AwsSdb::Service.new(:access_key_id => access_key, :secret_access_key => secret_key, :logger => Logger.new(@@logger))
|
57
80
|
@domains = Rudy::AWS::SimpleDB::Domains.new(@aws)
|
58
81
|
end
|
59
82
|
|
@@ -66,3 +89,15 @@ module Rudy
|
|
66
89
|
end
|
67
90
|
|
68
91
|
end
|
92
|
+
|
93
|
+
# Require EC2, S3, Simple DB class
|
94
|
+
begin
|
95
|
+
# TODO: Use autoload
|
96
|
+
Dir.glob(File.join(RUDY_LIB, 'rudy', 'aws', '{ec2,s3,sdb}', "*.rb")).each do |path|
|
97
|
+
require path
|
98
|
+
end
|
99
|
+
rescue LoadError => ex
|
100
|
+
puts "Error: #{ex.message}"
|
101
|
+
exit 1
|
102
|
+
end
|
103
|
+
|
data/lib/rudy/aws/ec2.rb
CHANGED
@@ -1,304 +1,28 @@
|
|
1
1
|
|
2
2
|
module Rudy::AWS
|
3
|
-
|
4
3
|
class EC2
|
5
|
-
|
6
|
-
|
7
|
-
end
|
8
|
-
|
9
|
-
class Images
|
10
|
-
include Rudy::AWS::ObjectBase
|
11
|
-
|
12
|
-
# Returns an array of hashes:
|
13
|
-
# {:aws_architecture=>"i386", :aws_owner=>"105148267242", :aws_id=>"ami-6fe40dd5",
|
14
|
-
# :aws_image_type=>"machine", :aws_location=>"bucket-name/your-image.manifest.xml",
|
15
|
-
# :aws_kernel_id=>"aki-a71cf9ce", :aws_state=>"available", :aws_ramdisk_id=>"ari-a51cf9cc",
|
16
|
-
# :aws_is_public=>false}
|
17
|
-
def list
|
18
|
-
@aws.describe_images_by_owner('self') || []
|
19
|
-
end
|
20
|
-
|
21
|
-
# +id+ AMI ID to deregister (ami-XXXXXXX)
|
22
|
-
# Returns true when successful. Otherwise throws an exception.
|
23
|
-
def deregister(id)
|
24
|
-
@aws.deregister_image(id)
|
25
|
-
end
|
26
|
-
|
27
|
-
# +path+ the S3 path to the manifest (bucket/file.manifest.xml)
|
28
|
-
# Returns the AMI ID when successful, otherwise throws an exception.
|
29
|
-
def register(path)
|
30
|
-
@aws.register_image(path)
|
31
|
-
end
|
32
|
-
end
|
33
|
-
class Snapshots
|
34
|
-
include Rudy::AWS::ObjectBase
|
35
|
-
|
36
|
-
def list
|
37
|
-
@aws.describe_snapshots || []
|
38
|
-
end
|
39
|
-
|
40
|
-
def create(vol_id)
|
41
|
-
@aws.create_snapshot(vol_id)
|
42
|
-
end
|
43
|
-
|
44
|
-
def destroy(snap_id)
|
45
|
-
@aws.delete_snapshot(snap_id)
|
46
|
-
end
|
47
|
-
|
48
|
-
def exists?(id)
|
49
|
-
list.each do |v|
|
50
|
-
return true if v[:aws_id] === id
|
51
|
-
end
|
52
|
-
false
|
53
|
-
end
|
54
|
-
|
55
|
-
end
|
56
|
-
|
57
|
-
class Volumes
|
58
|
-
include Rudy::AWS::ObjectBase
|
59
|
-
|
60
|
-
# [{:aws_device=>"/dev/sdr",
|
61
|
-
# :aws_attachment_status=>"attached",
|
62
|
-
# :snapshot_id=>nil,
|
63
|
-
# :aws_id=>"vol-6811f601",
|
64
|
-
# :aws_attached_at=>Wed Mar 11 07:06:44 UTC 2009,
|
65
|
-
# :aws_status=>"in-use",
|
66
|
-
# :aws_instance_id=>"i-0b2ab662",
|
67
|
-
# :aws_created_at=>Tue Mar 10 18:55:18 UTC 2009,
|
68
|
-
# :zone=>"us-east-1b",
|
69
|
-
# :aws_size=>10}]
|
70
|
-
def list
|
71
|
-
list = @aws.describe_volumes() || []
|
72
|
-
list.select { |v| v[:aws_status] != "deleting" }
|
73
|
-
end
|
74
|
-
|
75
|
-
def attach(inst_id, vol_id, device)
|
76
|
-
@aws.attach_volume(vol_id, inst_id, device)
|
77
|
-
end
|
78
|
-
|
79
|
-
def detach(vol_id)
|
80
|
-
@aws.detach_volume(vol_id)
|
81
|
-
end
|
82
|
-
|
83
|
-
def create(zone, size, snapshot=nil)
|
84
|
-
@aws.create_volume(snapshot, size, zone)
|
85
|
-
end
|
86
|
-
|
87
|
-
def destroy(vol_id)
|
88
|
-
@aws.delete_volume(vol_id)
|
89
|
-
end
|
90
|
-
|
91
|
-
def exists?(id)
|
92
|
-
list.each do |v|
|
93
|
-
return true if v[:aws_id] === id
|
94
|
-
end
|
95
|
-
false
|
96
|
-
end
|
97
|
-
|
98
|
-
def get(vol_id)
|
99
|
-
list = @aws.describe_volumes(vol_id) || []
|
100
|
-
list.first
|
101
|
-
end
|
102
|
-
|
103
|
-
def deleting?(vol_id)
|
104
|
-
return false unless vol_id
|
105
|
-
vol = get(vol_id)
|
106
|
-
(vol && vol[:aws_status] == "deleting")
|
107
|
-
end
|
108
|
-
|
109
|
-
def available?(vol_id)
|
110
|
-
return false unless vol_id
|
111
|
-
vol = get(vol_id)
|
112
|
-
(vol && vol[:aws_status] == "available")
|
113
|
-
end
|
114
|
-
|
115
|
-
def attached?(vol_id)
|
116
|
-
return false unless vol_id
|
117
|
-
vol = get(vol_id)
|
118
|
-
(vol && vol[:aws_status] == "in-use")
|
119
|
-
end
|
120
|
-
|
121
|
-
end
|
122
|
-
|
123
|
-
class Instances
|
124
|
-
include Rudy::AWS::ObjectBase
|
125
|
-
|
126
|
-
def destroy(*list)
|
127
|
-
begin
|
128
|
-
@aws.terminate_instances(list.flatten)
|
129
|
-
#rescue RightAws::AwsError => ex
|
130
|
-
# raise UnknownInstance.new
|
131
|
-
end
|
132
|
-
end
|
133
|
-
|
134
|
-
def restart(*list)
|
135
|
-
@aws.reboot_instances(list.flatten)
|
136
|
-
end
|
137
|
-
|
138
|
-
def attached_volume?(id, device)
|
139
|
-
list = volumes(id)
|
140
|
-
list.each do |v|
|
141
|
-
return true if v[:aws_device] == device
|
142
|
-
end
|
143
|
-
false
|
144
|
-
end
|
145
|
-
|
146
|
-
def volumes(id)
|
147
|
-
list = @aws.describe_volumes() || []
|
148
|
-
list.select { |v| v[:aws_status] != "deleting" && v[:aws_instance_id] === id }
|
149
|
-
end
|
150
|
-
|
151
|
-
def device_volume(id, device)
|
152
|
-
volumes.select { |v| v[:aws_device] === device }
|
153
|
-
end
|
154
|
-
|
155
|
-
def create(ami, group, keypair_name, user_data, zone)
|
156
|
-
@aws.run_instances(ami, 1, 1, [group], keypair_name, user_data, 'public', nil, nil, nil, zone)
|
157
|
-
end
|
158
|
-
|
159
|
-
# Creates a list of running instance IDs which are in a security group
|
160
|
-
# that matches +filter+.
|
161
|
-
# Returns a hash. The keys are instance IDs and the values are a hash
|
162
|
-
# of attributes associated to that instance.
|
163
|
-
# {:aws_state_code=>"16",
|
164
|
-
# :private_dns_name=>"domU-12-31-38-00-51-F1.compute-1.internal",
|
165
|
-
# :aws_instance_type=>"m1.small",
|
166
|
-
# :aws_reason=>"",
|
167
|
-
# :ami_launch_index=>"0",
|
168
|
-
# :aws_owner=>"207436219441",
|
169
|
-
# :aws_launch_time=>"2009-03-11T06:55:00.000Z",
|
170
|
-
# :aws_kernel_id=>"aki-a71cf9ce",
|
171
|
-
# :ssh_key_name=>"rilli-sexytime",
|
172
|
-
# :aws_reservation_id=>"r-66f5710f",
|
173
|
-
# :aws_state=>"running",
|
174
|
-
# :aws_ramdisk_id=>"ari-a51cf9cc",
|
175
|
-
# :aws_instance_id=>"i-0b2ab662",
|
176
|
-
# :aws_groups=>["rudydev-app"],
|
177
|
-
# :aws_availability_zone=>"us-east-1b",
|
178
|
-
# :aws_image_id=>"ami-daca2db3",
|
179
|
-
# :aws_product_codes=>[],
|
180
|
-
# :dns_name=>"ec2-67-202-9-30.compute-1.amazonaws.com"}
|
181
|
-
def list(filter='.')
|
182
|
-
filter = filter.to_s.downcase.tr('_|-', '.') # treat dashes, underscores as one
|
183
|
-
# Returns an array of hashes with the following keys:
|
184
|
-
# :aws_image_id, :aws_reason, :aws_state_code, :aws_owner, :aws_instance_id, :aws_reservation_id
|
185
|
-
# :aws_state, :dns_name, :ssh_key_name, :aws_groups, :private_dns_name, :aws_instance_type,
|
186
|
-
# :aws_launch_time, :aws_availability_zone :aws_kernel_id, :aws_ramdisk_id
|
187
|
-
instances = @aws.describe_instances || []
|
188
|
-
running_instances = {}
|
189
|
-
instances.each do |inst|
|
190
|
-
if inst[:aws_state] != "terminated" && (inst[:aws_groups].to_s =~ /#{filter}/)
|
191
|
-
running_instances[inst[:aws_instance_id]] = inst
|
192
|
-
end
|
193
|
-
end
|
194
|
-
running_instances
|
195
|
-
end
|
196
|
-
|
197
|
-
def get(inst_id)
|
198
|
-
# This is ridiculous. Send inst_id to describe volumes
|
199
|
-
instance = {}
|
200
|
-
list.each_pair do |id, hash|
|
201
|
-
next unless inst_id == id
|
202
|
-
instance = hash
|
203
|
-
end
|
204
|
-
instance
|
205
|
-
end
|
206
|
-
|
207
|
-
def running?(inst_id)
|
208
|
-
inst = get(inst_id)
|
209
|
-
(inst && inst[:aws_state] == "running")
|
210
|
-
end
|
211
|
-
|
212
|
-
def pending?(inst_id)
|
213
|
-
inst = get(inst_id)
|
214
|
-
(inst && inst[:aws_state] == "pending")
|
215
|
-
end
|
216
|
-
end
|
217
|
-
|
218
|
-
class Groups
|
219
|
-
include Rudy::AWS::ObjectBase
|
220
|
-
|
221
|
-
|
222
|
-
# +list+ is a list of security groups to look for. If it's empty, all groups
|
223
|
-
# associated to the account will be returned.
|
224
|
-
# right_aws returns an array of hashes
|
225
|
-
# :aws_group_name => "default-1",
|
226
|
-
# :aws_owner => "000000000888",
|
227
|
-
# :aws_description => "Default allowing SSH, HTTP, and HTTPS ingress",
|
228
|
-
# :aws_perms => [{:owner => "000000000888", :group => "default"},
|
229
|
-
# {:owner => "000000000888", :group => "default-1"},
|
230
|
-
# {:to_port => "-1", :protocol => "icmp", :from_port => "-1", :cidr_ips => "0.0.0.0/0"}]
|
231
|
-
# ]
|
232
|
-
def list(list=[])
|
233
|
-
glist = @aws.describe_security_groups(list) || []
|
4
|
+
@@logger = StringIO.new
|
234
5
|
|
235
|
-
|
236
|
-
|
237
|
-
|
238
|
-
|
239
|
-
|
240
|
-
|
241
|
-
|
242
|
-
|
243
|
-
|
244
|
-
|
245
|
-
|
246
|
-
|
247
|
-
|
248
|
-
|
249
|
-
|
250
|
-
|
251
|
-
|
252
|
-
|
253
|
-
end
|
254
|
-
|
255
|
-
|
256
|
-
# Does the security group +name+ exist?
|
257
|
-
def exists?(name)
|
258
|
-
begin
|
259
|
-
g = list([name.to_s])
|
260
|
-
|
261
|
-
rescue RightAws::AwsError => ex
|
262
|
-
# Ignore (it raises an exception when the list contains an unknown group name)
|
263
|
-
ensure
|
264
|
-
g ||= []
|
265
|
-
end
|
266
|
-
|
267
|
-
!g.empty?
|
268
|
-
end
|
269
|
-
|
270
|
-
end
|
271
|
-
|
272
|
-
class Addresses
|
273
|
-
include Rudy::AWS::ObjectBase
|
274
|
-
|
275
|
-
# Returns and array of hashes:
|
276
|
-
# [{:instance_id=>"i-d630cbbf", :public_ip=>"75.101.1.140"},
|
277
|
-
# {:instance_id=>nil, :public_ip=>"75.101.1.141"}]
|
278
|
-
def list
|
279
|
-
@aws.describe_addresses || []
|
280
|
-
end
|
281
|
-
|
282
|
-
|
283
|
-
# Associate an elastic IP to an instance
|
284
|
-
def associate(instance, address)
|
285
|
-
@aws.associate_address(instance, address)
|
286
|
-
end
|
287
|
-
|
288
|
-
def valid?(address)
|
289
|
-
list.each do |a|
|
290
|
-
return true if a[:public_ip] == address
|
291
|
-
end
|
292
|
-
false
|
293
|
-
end
|
294
|
-
|
295
|
-
def associated?(address)
|
296
|
-
list.each do |a|
|
297
|
-
return true if a[:public_ip] == address && a[:instance_id]
|
298
|
-
end
|
299
|
-
false
|
300
|
-
end
|
6
|
+
attr_reader :instances
|
7
|
+
attr_reader :images
|
8
|
+
attr_reader :addresses
|
9
|
+
attr_reader :groups
|
10
|
+
attr_reader :volumes
|
11
|
+
attr_reader :snapshots
|
12
|
+
attr_reader :aws
|
13
|
+
attr_reader :keypairs
|
14
|
+
|
15
|
+
def initialize(access_key, secret_key)
|
16
|
+
ec2 = ::EC2::Base.new(:access_key_id => access_key, :secret_access_key => secret_key)
|
17
|
+
@instances = Rudy::AWS::EC2::Instances.new(ec2)
|
18
|
+
@images = Rudy::AWS::EC2::Images.new(ec2)
|
19
|
+
@groups = Rudy::AWS::EC2::Groups.new(ec2)
|
20
|
+
@addresses = Rudy::AWS::EC2::Addresses.new(ec2)
|
21
|
+
@snapshots = Rudy::AWS::EC2::Snapshots.new(ec2)
|
22
|
+
@volumes = Rudy::AWS::EC2::Volumes.new(ec2)
|
23
|
+
@keypairs = Rudy::AWS::EC2::KeyPairs.new(ec2)
|
301
24
|
end
|
25
|
+
|
302
26
|
end
|
303
27
|
|
304
28
|
end
|
@@ -0,0 +1,121 @@
|
|
1
|
+
|
2
|
+
|
3
|
+
module Rudy::AWS
|
4
|
+
|
5
|
+
class EC2
|
6
|
+
|
7
|
+
class Address < Storable
|
8
|
+
field :ipaddress
|
9
|
+
field :instid
|
10
|
+
def to_s
|
11
|
+
msg = "Address: #{self.ipaddress}"
|
12
|
+
msg << ", instance: #{self.instid}" if self.instid
|
13
|
+
msg
|
14
|
+
end
|
15
|
+
end
|
16
|
+
|
17
|
+
class Addresses
|
18
|
+
include Rudy::AWS::ObjectBase
|
19
|
+
|
20
|
+
# Returns a Array of Rudy::AWS::EC2::Address objects.
|
21
|
+
def list(addresses=[])
|
22
|
+
addresses = list_as_hash(addresses)
|
23
|
+
addresses &&= addresses.values
|
24
|
+
addresses
|
25
|
+
end
|
26
|
+
|
27
|
+
# Returns a Hash of Rudy::AWS::EC2::Address objects. The key of the IP address.
|
28
|
+
def list_as_hash(addresses=[])
|
29
|
+
addresses ||= []
|
30
|
+
addresses = [addresses].flatten.compact
|
31
|
+
alist = @aws.describe_addresses(:addresses=> addresses)
|
32
|
+
|
33
|
+
return nil unless alist['addressesSet'].is_a?(Hash)
|
34
|
+
|
35
|
+
addresses = {}
|
36
|
+
alist['addressesSet']['item'].each do |address|
|
37
|
+
address = Addresses.from_hash(address)
|
38
|
+
addresses[address.ipaddress] = address
|
39
|
+
end
|
40
|
+
|
41
|
+
addresses
|
42
|
+
end
|
43
|
+
|
44
|
+
|
45
|
+
def any?
|
46
|
+
!(list_as_hash || {}).empty?
|
47
|
+
end
|
48
|
+
|
49
|
+
def get(address)
|
50
|
+
raise "Address cannot be nil" if address.nil?
|
51
|
+
address = address.ipaddress if address.is_a?(Rudy::AWS::EC2::Address)
|
52
|
+
(list(address) || []).first
|
53
|
+
end
|
54
|
+
|
55
|
+
def self.from_hash(h)
|
56
|
+
# requestId: 5ebcad80-eed9-4221-86f6-8d19d7acffe4
|
57
|
+
# addressesSet:
|
58
|
+
# item:
|
59
|
+
# - publicIp: 75.101.137.7
|
60
|
+
# instanceId:
|
61
|
+
address = Rudy::AWS::EC2::Address.new
|
62
|
+
address.ipaddress = h['publicIp']
|
63
|
+
address.instid = h['instanceId'] if h['instanceId'] && !h['instanceId'].empty?
|
64
|
+
address
|
65
|
+
end
|
66
|
+
|
67
|
+
# Associate an elastic IP to an instance
|
68
|
+
def associate(instance, address)
|
69
|
+
address = address.ipaddress if address.is_a?(Rudy::AWS::EC2::Address)
|
70
|
+
instance = instance.awsid if instance.is_a?(Rudy::AWS::EC2::Instance)
|
71
|
+
raise "Not a valid address" unless exists?(address)
|
72
|
+
opts ={
|
73
|
+
:instance_id => instance || raise("No instance ID supplied"),
|
74
|
+
:public_ip => address || raise("No public IP address supplied")
|
75
|
+
}
|
76
|
+
ret = @aws.associate_address(opts)
|
77
|
+
(ret && ret['return'] == 'true')
|
78
|
+
end
|
79
|
+
|
80
|
+
|
81
|
+
def create
|
82
|
+
ret = @aws.allocate_address
|
83
|
+
return false unless ret && ret['publicIp']
|
84
|
+
address = Rudy::AWS::EC2::Address.new
|
85
|
+
address.ipaddress = ret['publicIp']
|
86
|
+
address
|
87
|
+
end
|
88
|
+
|
89
|
+
def destroy(address)
|
90
|
+
address = address.ipaddress if address.is_a?(Rudy::AWS::EC2::Address)
|
91
|
+
raise "Not a valid address" unless exists?(address)
|
92
|
+
opts ={
|
93
|
+
:public_ip => address || raise("No public IP address supplied")
|
94
|
+
}
|
95
|
+
ret = @aws.release_address(opts)
|
96
|
+
(ret && ret['return'] == 'true')
|
97
|
+
end
|
98
|
+
|
99
|
+
|
100
|
+
# +address+ is an IP address or Rudy::AWS::EC2::Address object
|
101
|
+
# Returns true if the given address is assigned to the current account
|
102
|
+
def exists?(address)
|
103
|
+
address = address.ipaddress if address.is_a?(Rudy::AWS::EC2::Address)
|
104
|
+
list.each do |a|
|
105
|
+
return true if a.ipaddress == address
|
106
|
+
end
|
107
|
+
false
|
108
|
+
end
|
109
|
+
|
110
|
+
# +address+ is an IP address or Rudy::AWS::EC2::Address object
|
111
|
+
# Returns true if the given address is associated to an instance
|
112
|
+
def associated?(address)
|
113
|
+
address = address.ipaddress if address.is_a?(Rudy::AWS::EC2::Address)
|
114
|
+
list.each do |a|
|
115
|
+
return true if a.ipaddress == address && a.instid
|
116
|
+
end
|
117
|
+
false
|
118
|
+
end
|
119
|
+
end
|
120
|
+
end
|
121
|
+
end
|