rudy 0.8.5 → 0.9.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.
Files changed (132) hide show
  1. data/CHANGES.txt +110 -18
  2. data/README.rdoc +40 -44
  3. data/Rudyfile +35 -50
  4. data/bin/rudy +88 -57
  5. data/bin/rudy-ec2 +2 -16
  6. data/bin/rudy-s3 +0 -10
  7. data/bin/rudy-sdb +11 -12
  8. data/lib/rudy.rb +59 -91
  9. data/lib/rudy/aws.rb +4 -45
  10. data/lib/rudy/aws/ec2.rb +57 -20
  11. data/lib/rudy/aws/ec2/address.rb +10 -11
  12. data/lib/rudy/aws/ec2/group.rb +10 -9
  13. data/lib/rudy/aws/ec2/image.rb +8 -8
  14. data/lib/rudy/aws/ec2/instance.rb +18 -19
  15. data/lib/rudy/aws/ec2/keypair.rb +14 -19
  16. data/lib/rudy/aws/ec2/snapshot.rb +16 -9
  17. data/lib/rudy/aws/ec2/volume.rb +39 -26
  18. data/lib/rudy/aws/ec2/zone.rb +5 -4
  19. data/lib/rudy/aws/s3.rb +2 -1
  20. data/lib/rudy/aws/sdb.rb +35 -86
  21. data/lib/rudy/backups.rb +24 -0
  22. data/lib/rudy/cli.rb +5 -131
  23. data/lib/rudy/cli/aws/ec2/addresses.rb +19 -27
  24. data/lib/rudy/cli/aws/ec2/candy.rb +45 -20
  25. data/lib/rudy/cli/aws/ec2/groups.rb +9 -13
  26. data/lib/rudy/cli/aws/ec2/images.rb +5 -133
  27. data/lib/rudy/cli/aws/ec2/instances.rb +25 -25
  28. data/lib/rudy/cli/aws/ec2/keypairs.rb +7 -11
  29. data/lib/rudy/cli/aws/ec2/snapshots.rb +5 -9
  30. data/lib/rudy/cli/aws/ec2/volumes.rb +22 -23
  31. data/lib/rudy/cli/aws/ec2/zones.rb +2 -3
  32. data/lib/rudy/cli/aws/sdb/domains.rb +5 -6
  33. data/lib/rudy/cli/aws/sdb/objects.rb +33 -0
  34. data/lib/rudy/cli/aws/sdb/select.rb +23 -0
  35. data/lib/rudy/cli/backups.rb +38 -0
  36. data/lib/rudy/cli/base.rb +104 -0
  37. data/lib/rudy/cli/candy.rb +1 -2
  38. data/lib/rudy/cli/config.rb +20 -7
  39. data/lib/rudy/cli/disks.rb +7 -9
  40. data/lib/rudy/cli/execbase.rb +56 -0
  41. data/lib/rudy/cli/machines.rb +242 -45
  42. data/lib/rudy/cli/metadata.rb +24 -10
  43. data/lib/rudy/cli/networks.rb +34 -0
  44. data/lib/rudy/cli/routines.rb +32 -6
  45. data/lib/rudy/cli/status.rb +60 -0
  46. data/lib/rudy/config.rb +55 -32
  47. data/lib/rudy/config/objects.rb +44 -30
  48. data/lib/rudy/disks.rb +25 -0
  49. data/lib/rudy/exceptions.rb +99 -0
  50. data/lib/rudy/global.rb +67 -28
  51. data/lib/rudy/guidelines.rb +3 -2
  52. data/lib/rudy/huxtable.rb +67 -58
  53. data/lib/rudy/machines.rb +41 -263
  54. data/lib/rudy/metadata.rb +212 -38
  55. data/lib/rudy/metadata/backup.rb +123 -78
  56. data/lib/rudy/metadata/disk.rb +153 -170
  57. data/lib/rudy/metadata/machine.rb +179 -0
  58. data/lib/rudy/mixins.rb +2 -1
  59. data/lib/rudy/mixins/hash.rb +3 -1
  60. data/lib/rudy/mixins/symbol.rb +8 -0
  61. data/lib/rudy/routines.rb +127 -344
  62. data/lib/rudy/routines/base.rb +229 -0
  63. data/lib/rudy/routines/handlers/base.rb +48 -0
  64. data/lib/rudy/routines/handlers/depends.rb +49 -0
  65. data/lib/rudy/routines/handlers/disks.rb +249 -0
  66. data/lib/rudy/routines/handlers/group.rb +44 -0
  67. data/lib/rudy/routines/handlers/host.rb +70 -0
  68. data/lib/rudy/routines/handlers/keypair.rb +70 -0
  69. data/lib/rudy/routines/handlers/machines.rb +15 -0
  70. data/lib/rudy/routines/handlers/script.rb +85 -0
  71. data/lib/rudy/routines/handlers/user.rb +45 -0
  72. data/lib/rudy/routines/passthrough.rb +19 -23
  73. data/lib/rudy/routines/reboot.rb +98 -50
  74. data/lib/rudy/routines/shutdown.rb +65 -14
  75. data/lib/rudy/routines/startup.rb +112 -17
  76. data/lib/rudy/utils.rb +35 -68
  77. data/rudy.gemspec +82 -25
  78. data/tryouts/01_mixins/01_hash_tryouts.rb +20 -0
  79. data/tryouts/10_require_time/10_rudy_tryouts.rb +33 -0
  80. data/tryouts/10_require_time/15_global_tryouts.rb +58 -0
  81. data/tryouts/12_config/10_load_config_tryouts.rb +43 -0
  82. data/tryouts/12_config/20_defaults_tryouts.rb +16 -0
  83. data/tryouts/12_config/30_accounts_tryouts.rb +17 -0
  84. data/tryouts/12_config/40_machines_tryouts.rb +53 -0
  85. data/tryouts/12_config/50_commands_tryouts.rb +17 -0
  86. data/tryouts/12_config/60_routines_tryouts.rb +16 -0
  87. data/tryouts/15_huxtable/10_huxtable_tryouts.rb +47 -0
  88. data/tryouts/15_huxtable/20_user_tryouts.rb +47 -0
  89. data/tryouts/20_simpledb/10_domains_tryouts.rb +36 -0
  90. data/tryouts/20_simpledb/20_objects_tryouts.rb +56 -0
  91. data/tryouts/25_ec2/10_keypairs_tryouts.rb +54 -0
  92. data/tryouts/25_ec2/20_groups_tryouts.rb +56 -0
  93. data/tryouts/25_ec2/21_groups_authorize_address_tryouts.rb +53 -0
  94. data/tryouts/25_ec2/22_groups_authorize_account_tryouts.rb +54 -0
  95. data/tryouts/25_ec2/30_addresses_tryouts.rb +42 -0
  96. data/tryouts/25_ec2/40_volumes_tryouts.rb +53 -0
  97. data/tryouts/25_ec2/50_snapshots_tryouts.rb +75 -0
  98. data/tryouts/26_ec2_instances/10_instance_tryouts.rb +107 -0
  99. data/tryouts/26_ec2_instances/50_images_tryouts.rb +7 -0
  100. data/tryouts/30_metadata/10_include_tryouts.rb +45 -0
  101. data/tryouts/30_metadata/13_object_tryouts.rb +19 -0
  102. data/tryouts/30_metadata/50_disk_tryouts.rb +115 -0
  103. data/tryouts/30_metadata/51_disk_digest_tryouts.rb +24 -0
  104. data/tryouts/30_metadata/53_disk_list_tryouts.rb +35 -0
  105. data/tryouts/30_metadata/56_disk_volume_tryouts.rb +68 -0
  106. data/tryouts/30_metadata/60_backup_tryouts.rb +101 -0
  107. data/tryouts/30_metadata/63_backup_list_tryouts.rb +38 -0
  108. data/tryouts/30_metadata/64_backup_disk_tryouts.rb +65 -0
  109. data/tryouts/30_metadata/66_backup_snapshot_tryouts.rb +76 -0
  110. data/tryouts/30_metadata/70_machine_tryouts.rb +85 -0
  111. data/tryouts/30_metadata/73_machine_list_tryouts.rb +58 -0
  112. data/tryouts/30_metadata/76_machine_instance_tryouts.rb +64 -0
  113. data/tryouts/30_metadata/77_machines_tryouts.rb +45 -0
  114. data/tryouts/40_routines/10_keypair_handler_tryouts.rb +52 -0
  115. data/tryouts/40_routines/11_group_handler_tryouts.rb +36 -0
  116. data/tryouts/80_cli/10_rudyec2_tryouts.rb +8 -0
  117. data/tryouts/80_cli/60_rudy_tryouts.rb +41 -0
  118. data/tryouts/exploration/console.rb +91 -0
  119. data/tryouts/exploration/machine.rb +23 -0
  120. data/tryouts/failer +6 -0
  121. metadata +116 -32
  122. data/bin/ird +0 -153
  123. data/lib/rudy/metadata/backups.rb +0 -67
  124. data/lib/rudy/metadata/debug.rb +0 -38
  125. data/lib/rudy/metadata/disks.rb +0 -67
  126. data/lib/rudy/metadata/objectbase.rb +0 -108
  127. data/lib/rudy/routines/helper.rb +0 -76
  128. data/lib/rudy/routines/helpers/dependshelper.rb +0 -34
  129. data/lib/rudy/routines/helpers/diskhelper.rb +0 -403
  130. data/lib/rudy/routines/helpers/scripthelper.rb +0 -197
  131. data/lib/rudy/routines/helpers/userhelper.rb +0 -37
  132. data/support/rudy-ec2-startup +0 -200
@@ -1,113 +1,158 @@
1
- module Rudy::MetaData
2
- class Backup < Storable
3
- include Rudy::MetaData::ObjectBase
1
+
2
+ require 'date'
3
+
4
+ module Rudy
5
+ class Backup < Storable
6
+ include Rudy::Metadata
7
+ include Gibbler::Complex
4
8
 
5
9
  field :rtype
6
- field :awsid
10
+ field :snapid
11
+ field :volid
7
12
 
8
- field :region
9
- field :zone
10
- field :environment
11
- field :role
12
- field :position
13
13
  field :path
14
14
 
15
- field :date
16
- field :time
15
+ field :created => Time
16
+ field :year
17
+ field :month
18
+ field :day
19
+ field :hour
20
+ field :minute
17
21
  field :second
18
22
 
19
- field :created => Integer
20
-
23
+ field :user
21
24
  field :size
22
25
  field :fstype
23
- field :volume
24
-
25
- require 'date'
26
-
27
26
 
28
- def init(volume=nil, path=nil, position=nil)
29
- # NOTE: Arguments must be optional or Storable will raise an exception!
30
- @volume= volume
31
- @path = path
32
- @rtype = 'back'
33
- @region = @@global.region
34
- @zone = @@global.zone
35
- @environment = @@global.environment
36
- @role = @@global.role
37
- @position = position || @@global.position
27
+ # If one argument is supplied:
28
+ # * +path+ is a an absolute filesystem path
29
+ # * +opts+ is a hash of disk options.
30
+ #
31
+ # If two arguments are supplied:
32
+ # * +position+
33
+ # * +path+ is a an absolute filesystem path
34
+ # * +opts+ is a hash of disk options.
35
+ #
36
+ # Valid options are:
37
+ # * +:path+ is a an absolute filesystem path (overridden by +path+ arg)
38
+ # * +:position+ (overridden by +position+ arg)
39
+ # * +:created+ is an instance of Time
40
+ # * +:user+ is the name of the user which created the backup.
41
+ #
42
+ def initialize(position=nil, path=nil, opts={})
43
+ # Swap arg values if only one is supplied.
44
+ path, position = position, nil if !position.nil? && path.nil?
45
+ position ||= '01'
46
+
47
+ opts = {
48
+ :created => Time.now.utc,
49
+ :user => Rudy.sysinfo.user
50
+ }.merge opts
38
51
 
52
+ super Rudy::Backups::RTYPE, opts # Rudy::Metadata#initialize
39
53
 
40
- now = Time.now.utc
41
- datetime = Backup.format_timestamp(now).split(Rudy::DELIM)
42
- @created = now.to_i
43
- @date, @time, @second = datetime
54
+ @position, @path = position, path
44
55
 
45
56
  postprocess
57
+
46
58
  end
47
59
 
48
-
49
- def name
50
- sep=File::SEPARATOR
51
- dirs = @path.split sep if @path && !@path.empty?
52
- dirs.shift while dirs && (dirs[0].nil? || dirs[0].empty?)
53
- args = [dirs, @date, @time, @second].flatten
54
- super("back", @zone, @environment, @role, @position, *args)
60
+ def postprocess
61
+ @position &&= @position.to_s.rjust(2, '0')
62
+ @year = @created.year
63
+ @month = @created.month.to_s.rjust(2, '0')
64
+ @day = @created.mday.to_s.rjust(2, '0')
65
+ @hour = @created.hour.to_s.rjust(2, '0')
66
+ @minute = @created.min.to_s.rjust(2, '0')
67
+ @second = @created.sec.to_s.rjust(2, '0')
55
68
  end
56
69
 
57
- def nice_time
58
- return "" unless @date && @time
59
- t = @date.scan(/(\d\d\d\d)(\d\d)(\d\d)/).join('-')
60
- t << " " << @time.scan(/(\d\d)(\d\d)/).join(':')
61
- t
70
+ def to_s(with_titles=true)
71
+ "%s; %s" % [self.name, self.to_hash.inspect]
62
72
  end
63
73
 
64
- def to_s(*args)
65
- str = ""
66
- field_names.each do |key|
67
- str << sprintf(" %22s: %s#{$/}", key, self.send(key.to_sym))
74
+ def name
75
+ sep = File::SEPARATOR
76
+ dirs = @path.split sep if @path && !@path.empty?
77
+ unless @path == File::SEPARATOR
78
+ dirs.shift while dirs && (dirs[0].nil? || dirs[0].empty?)
68
79
  end
69
- str
70
- end
80
+ # Calls Rudy::Metadata#name with backup specific components
81
+ super [dirs, date, time, second]
82
+ end
71
83
 
72
- def disk
73
- rdisk = Rudy::Disks.new
74
- disk = Rudy::MetaData::Disk.new(@path, nil, nil, @position)
75
- disk.region, disk.zone = @region, @zone
76
- disk.environment, disk.role, disk.position = @environment, @role, @position
77
- diskobj = rdisk.get(disk.name)
78
- diskobj || disk
84
+ def date
85
+ "%s%s%s" % [@year, @month, @day]
86
+ end
87
+
88
+ def time
89
+ "%s%s" % [@hour, @minute]
79
90
  end
80
91
 
81
- def create(volume=nil)
82
- volume ||= @volume
83
- vol = @rsnap.create(volume)
84
- @awsid = vol.awsid
85
- self.save
92
+ def create
93
+ raise DuplicateRecord, self.name if exists?
94
+ disk = self.disk
95
+ ld "DISK: #{disk.name}"
96
+ raise Rudy::Backups::NoDisk, disk.name unless disk.exists?
97
+ @volid ||= disk.volid
98
+ snap = Rudy::AWS::EC2::Snapshots.create(@volid)
99
+ #snap = Rudy::AWS::EC2::Snapshots.list.first # debugging
100
+ ld "SNAP: #{snap.inspect}"
101
+ @snapid, @raw = snap.awsid, true
102
+ @size, @fstype = disk.size, disk.fstype
103
+ self.save :replace
86
104
  self
87
105
  end
88
106
 
89
- # 20090224-1813-36
90
- def Backup.format_timestamp(dat)
91
- mon, day, hour, min, sec = [dat.mon, dat.day, dat.hour, dat.min, dat.sec].collect { |v| v.to_s.rjust(2, "0") }
92
- [dat.year, mon, day, Rudy::DELIM, hour, min, Rudy::DELIM, sec].join
107
+ def restore
108
+ raise UnknownObject, self.name unless exists?
109
+ raise Rudy::Backups::NoBackup, self.name unless any?
110
+
93
111
  end
94
112
 
95
- def to_query(more=[], less=[])
96
- query = super([:path, :date, :time, :second, *more], less)
113
+ # Are there any backups for the associated disk?
114
+ def any?
115
+ backups = Rudy::Backups.list self.descriptors, [:year, :month, :day, :hour, :second]
116
+ !backups.nil?
97
117
  end
98
-
99
- def to_select(more=[], less=[])
100
- query = super([:path, :date, :time, :second, *more], less)
118
+
119
+ def descriptors
120
+ super :position, :path, :year, :month, :day, :hour, :second
101
121
  end
102
-
103
- # Does this disk have enough info to be saved or used?
104
- # The test is based on the same criteria for building
105
- # SimpleDB queries.
122
+
123
+ def destroy
124
+ Rudy::AWS::EC2::Snapshots.destroy(@snapid) if snapshot_exists?
125
+ super()
126
+ end
127
+
106
128
  def valid?
107
- criteria = build_criteria([:path]).flatten
108
- criteria.size == criteria.compact.size
129
+ !@path.nil? && !@path.empty? && @created.is_a?(Time) && !@volid.nil?
130
+ end
131
+
132
+ def disk
133
+ opts = {
134
+ :region => @region, :zone => @zone,
135
+ :environment => @environment, :role => @role,
136
+ :size => @size, :fstype => @fstype
137
+ }
138
+ disk = Rudy::Disk.new @position, @path, opts
139
+ disk.refresh! if disk.exists?
140
+ disk.size = @size
141
+ disk.fstype = @fstype
142
+ disk
143
+ end
144
+
145
+ def disk_exists?
146
+ self.disk.exists?
147
+ end
148
+
149
+ # Create snapshot_*? methods
150
+ %w[exists? completed?].each do |state|
151
+ define_method("snapshot_#{state}") do
152
+ return false if @snapid.nil? || @snapid.empty?
153
+ Rudy::AWS::EC2::Snapshots.send(state, @snapid)
154
+ end
109
155
  end
110
156
 
111
157
  end
112
- end
113
-
158
+ end
@@ -1,177 +1,160 @@
1
- module Rudy::MetaData
2
- class Disk < Storable
3
- include Rudy::MetaData::ObjectBase
4
-
5
-
6
- field :rtype
7
- field :awsid
8
- field :status
9
- field :instid
10
-
11
- field :region
12
- field :zone
13
- field :environment
14
- field :role
15
- field :position
16
- field :path
17
-
18
- field :device
19
- field :size
20
- #field :backups => Array
21
-
22
- # Is the associated volume formatted? One of: true, false, [empty].
23
- # [empty] means we don't know and it's the default.
24
- field :raw
25
-
26
- field :fstype
27
- field :mounted
28
-
29
- field :created
30
-
31
- def init(path=nil, size=1, device='/dev/sdh', position=nil)
32
- @path, @size, @device = path, size, device
33
- @rtype = 'disk'
34
- @region = @@global.region
35
- @zone = @@global.zone
36
- @environment = @@global.environment
37
- @role = @@global.role
38
- @position = position || @@global.position
39
- @mounted = false
40
-
41
- now = Time.now.utc
42
- datetime = Backup.format_timestamp(now).split(Rudy::DELIM)
43
- @created = now.to_i
44
-
45
- postprocess
46
- end
47
-
48
- def postprocess
49
- @size &&= @size.to_i
50
- @mounted = true if @mounted == "true"
51
- end
52
-
53
- def to_s(with_titles=true)
54
- update
55
- mtd = @mounted == true ? "mounted" : @status
56
- if @size && @device
57
- "%s; %3sGB; %s; %s" % [liner_note, @size, @device, mtd]
58
- else
59
- liner_note
1
+
2
+
3
+ module Rudy
4
+ class Disk < Storable
5
+ include Rudy::Metadata
6
+ include Gibbler::Complex
7
+
8
+ field :rtype
9
+ field :volid
10
+ field :status
11
+ field :instid
12
+
13
+ field :path
14
+
15
+ field :device
16
+ field :size
17
+ field :fstype
18
+
19
+ #field :backups => Array
20
+
21
+ # Is the associated volume formatted? One of: true, false
22
+ field :raw
23
+ field :mounted
24
+ field :created => Time
25
+
26
+ # If one argument is supplied:
27
+ # * +path+ is a an absolute filesystem path
28
+ # * +opts+ is a hash of disk options.
29
+ #
30
+ # If two arguments are supplied:
31
+ # * +position+
32
+ # * +path+ is a an absolute filesystem path
33
+ # * +opts+ is a hash of disk options.
34
+ #
35
+ # Valid options are:
36
+ # * +:path+ is a an absolute filesystem path (overridden by +path+ arg)
37
+ # * +:position+ (overridden by +position+ arg)
38
+ # * +:size+
39
+ # * +:device+
40
+ #
41
+ def initialize(position=nil, path=nil, opts={})
42
+ # Swap arg values if only one is supplied.
43
+ path, position = position, nil if !position.nil? && path.nil?
44
+ position ||= '01'
45
+
46
+ opts = {
47
+ :size => 1,
48
+ :device => '/dev/sdh'
49
+ }.merge opts
50
+
51
+ super Rudy::Disks::RTYPE, opts # Rudy::Metadata#initialize
52
+
53
+ @position, @path = position, path
54
+
55
+ # Defaults:
56
+ #datetime = Backup.format_timestamp(now).split(Rudy::DELIM)
57
+ @created = Time.now.utc
58
+ @mounted = false
59
+ postprocess
60
+
60
61
  end
61
- end
62
-
63
- def inspect
64
- lines = []
65
- lines << liner_note
66
- field_names.each do |key|
67
- next unless self.respond_to?(key)
68
- val = self.send(key)
69
- lines << sprintf(" %22s: %s", key, (val.is_a?(Array) ? val.join(', ') : val))
62
+
63
+ # sdb values are stored as strings. Some quick conversion.
64
+ def postprocess
65
+ @position &&= @position.to_s.rjust(2, '0')
66
+ @size &&= @size.to_i
67
+ @raw = true if @raw == "true" unless @raw.is_a?(TrueClass)
68
+ @mounted = (@mounted == "true") unless @mounted.is_a?(TrueClass)
70
69
  end
71
- lines.join($/)
72
- end
73
-
74
- def name
75
- sep=File::SEPARATOR
76
- dirs = @path.split sep if @path && !@path.empty?
77
- dirs.shift while dirs && (dirs[0].nil? || dirs[0].empty?)
78
- super("disk", @zone, @environment, @role, @position, *dirs)
79
- end
80
-
81
- def create(size=nil, zone=nil, snapshot=nil)
82
- raise "#{name} already exists" if exists?
83
- vol = @rvol.create(size || @size, zone || @zone, snapshot)
84
- @awsid = vol.awsid
85
- @raw = true
86
- self.save
87
- self
88
- end
89
-
90
- def backup
91
- raise "No volume to backup" unless @awsid
92
- bup = Rudy::MetaData::Backup.new(@awsid, @path, @position)
93
- bup.size = @size || 1
94
- bup.fstype = @fstype || 'ext3'
95
- bup.create
96
- end
97
-
98
- def list_backups
99
- rback = Rudy::Backups.new
100
- props = {
101
- :environment => @environment,
102
- :role => @role,
103
- :zone => @zone,
104
- :region => @region,
105
- :position => @position
106
- }
107
- rback.list([], [], props)
108
- end
109
-
110
- def attach(instid)
111
- raise "No volume id" unless exists?
112
- vol = @rvol.attach(@awsid, instid, @device)
113
- end
114
-
115
- def detach
116
- raise "No volume id" unless exists?
117
- vol = @rvol.detach(@awsid)
118
- end
119
-
120
- def destroy(force=false)
121
- if @awsid && !deleting?
122
- if !force
123
- raise Rudy::AWS::EC2::VolumeNotAvailable, @awsid if attached?
124
- else
125
- detach if exists? && attached?
126
- sleep 0.1
70
+
71
+ def to_s(with_titles=true)
72
+ self.name
73
+ end
74
+
75
+ def name
76
+ sep = File::SEPARATOR
77
+ dirs = @path.split sep if @path && !@path.empty?
78
+ unless @path == File::SEPARATOR
79
+ dirs.shift while dirs && (dirs[0].nil? || dirs[0].empty?)
127
80
  end
128
- raise Rudy::AWS::EC2::VolumeNotAvailable, @awsid if in_use?
129
- @rvol.destroy(@awsid) if exists? && available?
81
+ # Calls Rudy::Metadata#name with disk specific components
82
+ super *dirs
130
83
  end
131
- super() # quotes, otherwise Ruby will send this method's args
132
- end
133
-
134
- def update
135
- @awsid = nil if @awsid && @awsid.empty?
136
- @volume = @rvol.get(@awsid) if @awsid
137
- if @volume.is_a?(Rudy::AWS::EC2::Volume)
138
- @status = @volume.status
139
- @instid = @volume.instid
140
- save
141
- else
142
- @awsid, @status, @instid = nil, nil, nil
143
- @mounted = false # I don't like having to set this
144
- # Don't save it b/c it's possible the EC2 server is just down
84
+
85
+ def create(size=nil, zone=nil, snapshot=nil)
86
+ raise DuplicateRecord, self.name if exists?
87
+ vol = Rudy::AWS::EC2::Volumes.create(size || @size, zone || @zone, snapshot)
88
+ #vol = Rudy::AWS::EC2::Volumes.list(:available).first # debugging
89
+ @volid, @raw = vol.awsid, true
90
+ self.save :replace
91
+ self
145
92
  end
146
- end
147
-
148
- def to_query(more=[], less=[])
149
- super([:path, *more], less) # Add path to the default fields
150
- end
151
-
152
- def to_select(more=[], less=[])
153
- super([:path, *more], less)
154
- end
155
-
156
- # Does this disk have enough info to be saved or used?
157
- # The test is based on the same criteria for building
158
- # SimpleDB queries.
159
- def valid?
160
- criteria = build_criteria([:path]).flatten
161
- criteria.size == criteria.compact.size
162
- end
163
-
164
- def mounted?
165
- @mounted && @mounted == true
166
- end
167
-
168
-
169
- %w[exists? deleting? available? attached? in_use?].each do |state|
170
- define_method(state) do
171
- return false if @awsid.nil? || @awsid.empty?
172
- @rvol.send(state, @awsid) rescue false # deleting?, available?, etc...
93
+
94
+ def archive
95
+ raise Rudy::AWS::EC2::VolumeNotAvailable, @volid unless volume_attached?
96
+ back = Rudy::Backup.new @position, @path, self.descriptors
97
+ back.create
98
+ back.size, back.fstype = @size, @fstype
99
+ back.save :replace
100
+ back
101
+ end
102
+
103
+ def backups
104
+ Rudy::Backups.list self.descriptors
105
+ end
106
+
107
+
108
+ def destroy(force=false)
109
+ if @volid && !volume_deleting?
110
+ if !force
111
+ raise Rudy::AWS::EC2::VolumeNotAvailable, @volid if volume_attached?
112
+ else
113
+ volume_detach if volume_exists? && volume_attached?
114
+ sleep 0.1
115
+ end
116
+ raise Rudy::AWS::EC2::VolumeNotAvailable, @volid if volume_in_use?
117
+ Rudy::AWS::EC2::Volumes.destroy(@volid) if volume_exists? && volume_available?
118
+ end
119
+ super() # quotes, otherwise Ruby will send this method's args
120
+ end
121
+
122
+ def descriptors
123
+ super :position, :path
124
+ end
125
+
126
+
127
+
128
+ def valid?
129
+ !@path.nil? && !@path.empty?
173
130
  end
131
+
132
+
133
+ def volume_attach(instid)
134
+ raise Rudy::Error, "No volume id" unless volume_exists?
135
+ vol = Rudy::AWS::EC2::Volumes.attach(@volid, instid, @device)
136
+ end
137
+
138
+ def volume_detach
139
+ raise Rudy::Error, "No volume id" unless volume_exists?
140
+ vol = Rudy::AWS::EC2::Volumes.detach(@volid)
141
+ end
142
+
143
+ def raw?
144
+ @raw == true
145
+ end
146
+
147
+ def mounted?
148
+ @mounted == true
149
+ end
150
+
151
+ # Create volume_*? methods
152
+ %w[exists? deleting? available? attached? in_use?].each do |state|
153
+ define_method("volume_#{state}") do
154
+ return false if @volid.nil? || @volid.empty?
155
+ Rudy::AWS::EC2::Volumes.send(state, @volid) rescue false # deleting?, available?, etc...
156
+ end
157
+ end
158
+
174
159
  end
175
-
176
- end
177
- end
160
+ end