rackspace_cloud 0.4.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- data/MIT-LICENSE +20 -0
- data/README +21 -0
- data/Rakefile +31 -0
- data/VERSION +1 -0
- data/init.rb +0 -0
- data/install.rb +0 -0
- data/lib/rackspace_cloud.rb +44 -0
- data/lib/rackspace_cloud/base.rb +136 -0
- data/lib/rackspace_cloud/flavor.rb +17 -0
- data/lib/rackspace_cloud/image.rb +52 -0
- data/lib/rackspace_cloud/server.rb +88 -0
- data/lib/rackspace_cloud/shared_ip_group.rb +33 -0
- data/rackspace_cloud.gemspec +56 -0
- data/test/authentication_test.rb +10 -0
- data/test/configuration_test.rb +27 -0
- data/test/test_helper.rb +11 -0
- metadata +81 -0
data/MIT-LICENSE
ADDED
@@ -0,0 +1,20 @@
|
|
1
|
+
Copyright (c) 2006 Cosmin Radoi
|
2
|
+
|
3
|
+
Permission is hereby granted, free of charge, to any person obtaining
|
4
|
+
a copy of this software and associated documentation files (the
|
5
|
+
"Software"), to deal in the Software without restriction, including
|
6
|
+
without limitation the rights to use, copy, modify, merge, publish,
|
7
|
+
distribute, sublicense, and/or sell copies of the Software, and to
|
8
|
+
permit persons to whom the Software is furnished to do so, subject to
|
9
|
+
the following conditions:
|
10
|
+
|
11
|
+
The above copyright notice and this permission notice shall be
|
12
|
+
included in all copies or substantial portions of the Software.
|
13
|
+
|
14
|
+
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
|
15
|
+
EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
|
16
|
+
MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
|
17
|
+
NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
|
18
|
+
LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
|
19
|
+
OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
|
20
|
+
WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
|
data/README
ADDED
@@ -0,0 +1,21 @@
|
|
1
|
+
Example:
|
2
|
+
|
3
|
+
>> require 'rackspace_cloud'
|
4
|
+
>> cloud = RackspaceCloud::Base.new(:user => "gomer", :access_key => "aabbccddaabbccddaabbccdd")
|
5
|
+
=> #<RackspaceCloud::Base:0x1065f44 @access_key="aabbccddaabbccddaabbccdd", @user="gomer">
|
6
|
+
>> cloud.connect
|
7
|
+
=> nil
|
8
|
+
>> cloud.servers
|
9
|
+
=> []
|
10
|
+
>> new_server = cloud.create_server('development', 1, 8) # create a 256MB Ubuntu 9.04 instance)
|
11
|
+
=> #<RackspaceCloud::Server:0x1054a78 @image=#<RackspaceCloud::Image:0x10598e8 @name="Ubuntu 9.04 (jaunty)", @updated="2009-07-20T09:14:37-05:00", @created="2009-07-20T09:14:37-05:00", @status="ACTIVE", @rackspace_id=8>, @public_ips=["174.xxx.xxx.xxx"], @flavor=#<RackspaceCloud::Flavor:0x105d40c @name="256 slice", @ram=256, @disk=10, @rackspace_id=1>, @name="development", @progress=80, @adminPass="developmentU5fG3", @host_id="a7765fde333eead221", @private_ips=["10.xxx.xxx.xxx"], @rackspace_id=1, @status="BUILD">
|
12
|
+
|
13
|
+
... wait a while ...
|
14
|
+
|
15
|
+
>> new_server.refresh.status
|
16
|
+
=> "ACTIVE"
|
17
|
+
>> new_server.hard_reboot
|
18
|
+
=> nil
|
19
|
+
>> new_server.refresh.status
|
20
|
+
=> "HARD_REBOOT"
|
21
|
+
|
data/Rakefile
ADDED
@@ -0,0 +1,31 @@
|
|
1
|
+
require 'rubygems'
|
2
|
+
require 'rake'
|
3
|
+
require 'rake/testtask'
|
4
|
+
|
5
|
+
task :default => :test
|
6
|
+
|
7
|
+
Rake::TestTask.new(:test) do |test|
|
8
|
+
test.libs << 'lib' << 'test'
|
9
|
+
test.pattern = 'test/**/*_test.rb'
|
10
|
+
test.verbose = true
|
11
|
+
end
|
12
|
+
|
13
|
+
begin
|
14
|
+
require 'jeweler'
|
15
|
+
Jeweler::Tasks.new do |gemspec|
|
16
|
+
gemspec.name = "rackspace_cloud"
|
17
|
+
gemspec.summary = "Gem enabling the management of Rackspace Cloud Server instances"
|
18
|
+
gemspec.description = "Gem enabling the management of Rackspace Cloud Server instances."
|
19
|
+
gemspec.email = "grant@moreblinktag.com"
|
20
|
+
gemspec.homepage = "http://github.com/ggoodale/rackspace_cloud"
|
21
|
+
gemspec.authors = ["Grant Goodale"]
|
22
|
+
gemspec.files.exclude("**/.gitignore")
|
23
|
+
gemspec.add_dependency('patron', '>= 0.4.0')
|
24
|
+
gemspec.add_development_dependency('shoulda', '>= 2.10')
|
25
|
+
gemspec.add_development_dependency('mocha', '>= 0.9.4')
|
26
|
+
end
|
27
|
+
rescue LoadError
|
28
|
+
puts "Jeweler not available. Install it with: sudo gem install technicalpickles-jeweler -s http://gems.github.com"
|
29
|
+
end
|
30
|
+
|
31
|
+
|
data/VERSION
ADDED
@@ -0,0 +1 @@
|
|
1
|
+
0.4.0
|
data/init.rb
ADDED
File without changes
|
data/install.rb
ADDED
File without changes
|
@@ -0,0 +1,44 @@
|
|
1
|
+
require "patron"
|
2
|
+
require "json"
|
3
|
+
require "uri"
|
4
|
+
require "digest/sha1"
|
5
|
+
require "base64"
|
6
|
+
|
7
|
+
# Bring in all of our submodules
|
8
|
+
Dir[File.join(File.dirname(__FILE__), 'rackspace_cloud/**/*.rb')].sort.each { |lib| require lib }
|
9
|
+
|
10
|
+
module RackspaceCloud
|
11
|
+
|
12
|
+
class APIVersionError < StandardError; end
|
13
|
+
class ConfigurationError < StandardError; end
|
14
|
+
class AuthorizationError < StandardError; end
|
15
|
+
|
16
|
+
API_VERSION = "1.0"
|
17
|
+
BASE_AUTH_URI = "https://auth.api.rackspacecloud.com"
|
18
|
+
|
19
|
+
def RackspaceCloud.auth_url
|
20
|
+
@@auth_uri ||= URI.parse("#{BASE_AUTH_URI}/v#{API_VERSION}")
|
21
|
+
end
|
22
|
+
|
23
|
+
protected
|
24
|
+
|
25
|
+
def RackspaceCloud.check_version_compatibility
|
26
|
+
#This should eventually check the versions and raise an APIVersionError if there's a mismatch.
|
27
|
+
end
|
28
|
+
|
29
|
+
def RackspaceCloud.request_authorization(user, access_key)
|
30
|
+
session = Patron::Session.new
|
31
|
+
session.base_url = BASE_AUTH_URI
|
32
|
+
session.headers["X-Auth-User"] = user
|
33
|
+
session.headers["X-Auth-Key"] = access_key
|
34
|
+
session.headers["User-Agent"] = "rackspacecloud_ruby_gem"
|
35
|
+
response = session.get("/v#{API_VERSION}")
|
36
|
+
|
37
|
+
case response.status
|
38
|
+
when 204 # "No Content", which means success
|
39
|
+
response.headers
|
40
|
+
else
|
41
|
+
raise AuthorizationError, "Error during authorization: #{response.status}"
|
42
|
+
end
|
43
|
+
end
|
44
|
+
end
|
@@ -0,0 +1,136 @@
|
|
1
|
+
module RackspaceCloud
|
2
|
+
class Base
|
3
|
+
attr_reader :user, :access_key, :auth_token
|
4
|
+
|
5
|
+
def initialize(config={})
|
6
|
+
validate_config(config)
|
7
|
+
@user = config[:user]
|
8
|
+
@access_key = config[:access_key]
|
9
|
+
@authorized = false
|
10
|
+
end
|
11
|
+
|
12
|
+
def connect
|
13
|
+
configure_service_urls(RackspaceCloud.request_authorization(@user, @access_key))
|
14
|
+
RackspaceCloud.check_version_compatibility
|
15
|
+
@authorized = true
|
16
|
+
populate_flavors
|
17
|
+
populate_images
|
18
|
+
get_limits
|
19
|
+
end
|
20
|
+
|
21
|
+
def authorized?
|
22
|
+
@authorized
|
23
|
+
end
|
24
|
+
|
25
|
+
# storage for the lists of flavors and images we request at auth time
|
26
|
+
attr_reader :flavors
|
27
|
+
def populate_flavors
|
28
|
+
@flavors ||= {}
|
29
|
+
request("/flavors/detail")['flavors'].each do |flavor|
|
30
|
+
@flavors[flavor['id']] = RackspaceCloud::Flavor.new(flavor)
|
31
|
+
end
|
32
|
+
nil
|
33
|
+
end
|
34
|
+
|
35
|
+
attr_reader :images
|
36
|
+
def populate_images
|
37
|
+
@images ||= {}
|
38
|
+
request("/images/detail")['images'].each do |image|
|
39
|
+
@images[image['id']] = RackspaceCloud::Image.new(self, image)
|
40
|
+
end
|
41
|
+
nil
|
42
|
+
end
|
43
|
+
|
44
|
+
attr_reader :limits
|
45
|
+
def get_limits
|
46
|
+
@limits ||= {}
|
47
|
+
@limits.merge!(request("/limits")['limits'])
|
48
|
+
nil
|
49
|
+
end
|
50
|
+
|
51
|
+
def servers
|
52
|
+
request("/servers/detail")["servers"].collect {|server_json|
|
53
|
+
RackspaceCloud::Server.new(self, server_json)
|
54
|
+
}
|
55
|
+
end
|
56
|
+
|
57
|
+
def create_server(name, flavor, image, metadata={}, personality=[])
|
58
|
+
new_server_data = {'server' => {
|
59
|
+
'name' => name,
|
60
|
+
'flavorId' => flavor.to_i,
|
61
|
+
'imageId' => image.to_i,
|
62
|
+
'metadata' => metadata,
|
63
|
+
'personality' => personality
|
64
|
+
}}
|
65
|
+
|
66
|
+
RackspaceCloud::Server.new(self, request("/servers", :method => :post, :data => new_server_data)['server'])
|
67
|
+
end
|
68
|
+
|
69
|
+
def shared_ip_groups
|
70
|
+
request("/shared_ip_groups/detail")['sharedIpGroups'].collect {|group_json|
|
71
|
+
RackspaceCloud::SharedIPGroup.new(self, group_json)
|
72
|
+
}
|
73
|
+
end
|
74
|
+
|
75
|
+
# Yes, you can only specify at most a single server to initially populate a shared IP group. Odd, that.
|
76
|
+
def create_shared_ip_group(name, server=nil)
|
77
|
+
new_group_data = {'sharedIpGroup' => {'name' => name, 'server' => server}}
|
78
|
+
new_group_data['sharedIpGroup']['server'] = server.to_i unless server.nil?
|
79
|
+
RackspaceCloud::SharedIPGroup.new(self, request("/shared_ip_groups", :method => :post, :data => new_group_data))
|
80
|
+
end
|
81
|
+
|
82
|
+
def request(path, options={})
|
83
|
+
raise RuntimeError, "Please authorize before using by calling connect()" unless authorized?
|
84
|
+
@session ||= begin
|
85
|
+
s = Patron::Session.new
|
86
|
+
s.base_url = @server_management_url
|
87
|
+
s.headers['X-Auth-Token'] = @auth_token
|
88
|
+
s.headers["User-Agent"] = "rackspacecloud_ruby_gem"
|
89
|
+
s.timeout = 10
|
90
|
+
s
|
91
|
+
end
|
92
|
+
response = case options[:method]
|
93
|
+
when :post
|
94
|
+
@session.headers['Accept'] = "application/json"
|
95
|
+
@session.headers['Content-Type'] = "application/json"
|
96
|
+
@session.post("#{path}", options[:data].to_json)
|
97
|
+
when :put
|
98
|
+
@session.headers['Content-Type'] = "application/json"
|
99
|
+
@session.put("#{path}", options[:data].to_json)
|
100
|
+
when :delete
|
101
|
+
@session.delete("#{path}")
|
102
|
+
else
|
103
|
+
@session.get("#{path}.json")
|
104
|
+
end
|
105
|
+
|
106
|
+
case response.status
|
107
|
+
when 200, 201, 202, 204
|
108
|
+
JSON.parse(response.body) unless response.body.empty?
|
109
|
+
else
|
110
|
+
puts response.body
|
111
|
+
raise RuntimeError, "Error fetching #{path}: #{response.status}"
|
112
|
+
end
|
113
|
+
end
|
114
|
+
|
115
|
+
def api_version
|
116
|
+
RackspaceCloud::API_VERSION
|
117
|
+
end
|
118
|
+
|
119
|
+
protected
|
120
|
+
|
121
|
+
def validate_config(config)
|
122
|
+
errors = []
|
123
|
+
(config[:user] && config[:user].length) || errors << "missing username"
|
124
|
+
(config[:access_key] && config[:access_key].length) || errors << "missing access_key"
|
125
|
+
raise(ArgumentError, "Error: invalid configuration: #{errors.join(';')}") unless errors.empty?
|
126
|
+
end
|
127
|
+
|
128
|
+
def configure_service_urls(url_hash = {})
|
129
|
+
@server_management_url = url_hash['X-Server-Management-Url']
|
130
|
+
@storage_url = url_hash['X-Storage-Url']
|
131
|
+
@storage_token = url_hash['X-Storage-Token']
|
132
|
+
@cdn_management_url = url_hash['X-CDN-Management-Url']
|
133
|
+
@auth_token = url_hash['X-Auth-Token']
|
134
|
+
end
|
135
|
+
end
|
136
|
+
end
|
@@ -0,0 +1,17 @@
|
|
1
|
+
module RackspaceCloud
|
2
|
+
class Flavor
|
3
|
+
attr_reader :name, :disk, :ram, :rackspace_id
|
4
|
+
|
5
|
+
def initialize(flavor_json)
|
6
|
+
@rackspace_id = flavor_json['id']
|
7
|
+
@name = flavor_json['name']
|
8
|
+
@disk = flavor_json['disk']
|
9
|
+
@ram = flavor_json['ram']
|
10
|
+
end
|
11
|
+
|
12
|
+
def to_i
|
13
|
+
@rackspace_id
|
14
|
+
end
|
15
|
+
end
|
16
|
+
end
|
17
|
+
|
@@ -0,0 +1,52 @@
|
|
1
|
+
module RackspaceCloud
|
2
|
+
class Image
|
3
|
+
|
4
|
+
MAX_RACKSPACE_IMAGE_ID = 10 # the highest id in use by a standard rackspace image (vs. a user backup)
|
5
|
+
|
6
|
+
attr_reader :name, :created, :updated, :status, :progress, :rackspace_id, :base
|
7
|
+
|
8
|
+
class << self
|
9
|
+
def create_from_server(server, name=nil)
|
10
|
+
name ||= generate_timestamped_name(server)
|
11
|
+
image_json = server.base.request("/images", :method => :post, :data => {'image' => {'name' => name, 'serverId' => @rackspace_id}})['image']
|
12
|
+
new_image = RackspaceCloud::Image.new(image_json)
|
13
|
+
@images[new_image.rackspace_id] = new_image
|
14
|
+
new_image
|
15
|
+
end
|
16
|
+
end
|
17
|
+
|
18
|
+
def initialize(base, image_json)
|
19
|
+
@base = base
|
20
|
+
populate(image_json)
|
21
|
+
end
|
22
|
+
|
23
|
+
def delete
|
24
|
+
raise RuntimeError, "Can't delete Rackspace standard images" if @rackspace_id <= MAX_RACKSPACE_IMAGE_ID
|
25
|
+
@base.request("/images/#{@rackspace_id}", :method => :delete)
|
26
|
+
end
|
27
|
+
|
28
|
+
def to_i
|
29
|
+
@rackspace_id
|
30
|
+
end
|
31
|
+
|
32
|
+
def refresh
|
33
|
+
populate(@base.request("/images/#{@rackspace_id}")['image'])
|
34
|
+
self
|
35
|
+
end
|
36
|
+
|
37
|
+
protected
|
38
|
+
|
39
|
+
def populate(image_json)
|
40
|
+
@rackspace_id = image_json['id']
|
41
|
+
@name = image_json['name']
|
42
|
+
@created = DateTime.parse(image_json['created'])
|
43
|
+
@updated = DateTime.parse(image_json['updated'])
|
44
|
+
@status = image_json['status']
|
45
|
+
@progress = image_json['progress']
|
46
|
+
end
|
47
|
+
|
48
|
+
def generate_timestamped_name(server)
|
49
|
+
"#{server.downcase.gsub!(/\W/, "-")}-#{Time.nowTime.now.strftime('%Y%m%d%H%M%S%z')}"
|
50
|
+
end
|
51
|
+
end
|
52
|
+
end
|
@@ -0,0 +1,88 @@
|
|
1
|
+
module RackspaceCloud
|
2
|
+
class Server
|
3
|
+
attr_reader :name, :status, :flavor, :image, :base
|
4
|
+
attr_reader :rackspace_id, :host_id, :progress
|
5
|
+
attr_reader :public_ips, :private_ips, :adminPass
|
6
|
+
|
7
|
+
STATUS_VALUES = %w{ACTIVE BUILD REBUILD SUSPENDED QUEUE_RESIZE PREP_RESIZE VERIFY_RESIZE PASSWORD RESCUE REBOOT HARD_REBOOT SHARE_IP SHARE_IP_NO_CONFIG DELETE_IP UNKNOWN}
|
8
|
+
|
9
|
+
def initialize(base, server_json)
|
10
|
+
@base = base
|
11
|
+
populate(server_json)
|
12
|
+
end
|
13
|
+
|
14
|
+
def ready?
|
15
|
+
self.refresh.status == 'ACTIVE'
|
16
|
+
end
|
17
|
+
|
18
|
+
def reboot
|
19
|
+
action_request('reboot' => {'type' => 'SOFT'})
|
20
|
+
end
|
21
|
+
|
22
|
+
def hard_reboot
|
23
|
+
action_request('reboot' => {'type' => 'HARD'})
|
24
|
+
end
|
25
|
+
|
26
|
+
def rebuild(new_image=nil)
|
27
|
+
action_request('rebuild' => {'imageId' => new_image ? new_image.to_i : image.to_i})
|
28
|
+
end
|
29
|
+
|
30
|
+
def resize(new_flavor)
|
31
|
+
action_request('resize' => {'flavorId' => new_flavor.to_i})
|
32
|
+
end
|
33
|
+
|
34
|
+
def confirm_resize
|
35
|
+
action_request('confirmResize' => nil)
|
36
|
+
end
|
37
|
+
|
38
|
+
def revert_resize
|
39
|
+
action_request('revertResize' => nil)
|
40
|
+
end
|
41
|
+
|
42
|
+
def share_ip_address(ip_address, shared_ip_address_group, configure_server = true)
|
43
|
+
@base.request("/servers/#{@rackspace_id}/ips/public/#{ip_address}",
|
44
|
+
:method => :put, :data => {'shareIp' => {'sharedIpGroupId' => shared_ip_address_group.to_i, 'configureServer' => configure_server}})
|
45
|
+
end
|
46
|
+
|
47
|
+
def unshare_ip_address(ip_address)
|
48
|
+
@base.request("/servers/#{@rackspace_id}/ips/public/#{ip_address}", :method => :delete)
|
49
|
+
end
|
50
|
+
|
51
|
+
def delete
|
52
|
+
@base.request("/servers/#{@rackspace_id}", :method => :delete)
|
53
|
+
end
|
54
|
+
|
55
|
+
def update_server_name(new_name)
|
56
|
+
@base.request("/servers/#{@rackspace_id}", :method => :put, :data => {"server" => {"name" => new_name}})
|
57
|
+
end
|
58
|
+
|
59
|
+
def update_admin_password(new_password)
|
60
|
+
@base.request("/servers/#{@rackspace_id}", :method => :put, :data => {"server" => {"adminPass" => new_password}})
|
61
|
+
end
|
62
|
+
|
63
|
+
# update this server's status and progress by calling /servers/<id>
|
64
|
+
def refresh
|
65
|
+
populate(@base.request("/servers/#{@rackspace_id}")['server'])
|
66
|
+
self
|
67
|
+
end
|
68
|
+
|
69
|
+
protected
|
70
|
+
|
71
|
+
def action_request(data)
|
72
|
+
@base.request("/servers/#{@rackspace_id}/action", :method => :post, :data => data)
|
73
|
+
end
|
74
|
+
|
75
|
+
def populate(server_json)
|
76
|
+
@name = server_json['name']
|
77
|
+
@status = server_json['status']
|
78
|
+
@flavor = @base.flavors[server_json['flavorId']]
|
79
|
+
@image = @base.images[server_json['imageId']]
|
80
|
+
@rackspace_id = server_json['id']
|
81
|
+
@host_id = server_json['hostId']
|
82
|
+
@progress = server_json['progress']
|
83
|
+
@public_ips = server_json['addresses']['public']
|
84
|
+
@private_ips = server_json['addresses']['private']
|
85
|
+
@adminPass = server_json['adminPass']
|
86
|
+
end
|
87
|
+
end
|
88
|
+
end
|
@@ -0,0 +1,33 @@
|
|
1
|
+
module RackspaceCloud
|
2
|
+
class SharedIPGroup
|
3
|
+
attr_reader :rackspace_id, :name, :servers
|
4
|
+
|
5
|
+
def initialize(base, group_json)
|
6
|
+
@base = base
|
7
|
+
populate(group_json)
|
8
|
+
end
|
9
|
+
|
10
|
+
def delete
|
11
|
+
@base.request("/shared_ip_groups/#{@rackspace_id}", :method => :delete)
|
12
|
+
end
|
13
|
+
|
14
|
+
def refresh
|
15
|
+
populate(@base.request("/shared_ip_groups/detail")['sharedIpGroup'])
|
16
|
+
end
|
17
|
+
|
18
|
+
def to_i
|
19
|
+
@rackspace_id
|
20
|
+
end
|
21
|
+
|
22
|
+
protected
|
23
|
+
|
24
|
+
def populate(group_json)
|
25
|
+
puts group_json.inspect
|
26
|
+
@rackspace_id = group_json['id']
|
27
|
+
@name = group_json['name']
|
28
|
+
unless group_json['servers'].nil?
|
29
|
+
@servers = @base.servers.select{|server| group_json['servers'].include? server.rackspace_id}
|
30
|
+
end
|
31
|
+
end
|
32
|
+
end
|
33
|
+
end
|
@@ -0,0 +1,56 @@
|
|
1
|
+
# -*- encoding: utf-8 -*-
|
2
|
+
|
3
|
+
Gem::Specification.new do |s|
|
4
|
+
s.name = %q{rackspace_cloud}
|
5
|
+
s.version = "0.4.0"
|
6
|
+
|
7
|
+
s.required_rubygems_version = Gem::Requirement.new(">= 0") if s.respond_to? :required_rubygems_version=
|
8
|
+
s.authors = ["Grant Goodale"]
|
9
|
+
s.date = %q{2009-08-03}
|
10
|
+
s.description = %q{Gem enabling the management of Rackspace Cloud Server instances.}
|
11
|
+
s.email = %q{grant@moreblinktag.com}
|
12
|
+
s.extra_rdoc_files = [
|
13
|
+
"README"
|
14
|
+
]
|
15
|
+
s.files = [
|
16
|
+
"MIT-LICENSE",
|
17
|
+
"README",
|
18
|
+
"Rakefile",
|
19
|
+
"VERSION",
|
20
|
+
"init.rb",
|
21
|
+
"install.rb",
|
22
|
+
"lib/rackspace_cloud.rb",
|
23
|
+
"lib/rackspace_cloud/base.rb",
|
24
|
+
"lib/rackspace_cloud/flavor.rb",
|
25
|
+
"lib/rackspace_cloud/image.rb",
|
26
|
+
"lib/rackspace_cloud/server.rb",
|
27
|
+
"lib/rackspace_cloud/shared_ip_group.rb",
|
28
|
+
"rackspace_cloud.gemspec",
|
29
|
+
"test/authentication_test.rb",
|
30
|
+
"test/configuration_test.rb",
|
31
|
+
"test/test_helper.rb"
|
32
|
+
]
|
33
|
+
s.homepage = %q{http://github.com/ggoodale/rackspace_cloud}
|
34
|
+
s.rdoc_options = ["--charset=UTF-8"]
|
35
|
+
s.require_paths = ["lib"]
|
36
|
+
s.rubygems_version = %q{1.3.3}
|
37
|
+
s.summary = %q{Gem enabling the management of Rackspace Cloud Server instances}
|
38
|
+
s.test_files = [
|
39
|
+
"test/authentication_test.rb",
|
40
|
+
"test/configuration_test.rb",
|
41
|
+
"test/test_helper.rb"
|
42
|
+
]
|
43
|
+
|
44
|
+
if s.respond_to? :specification_version then
|
45
|
+
current_version = Gem::Specification::CURRENT_SPECIFICATION_VERSION
|
46
|
+
s.specification_version = 3
|
47
|
+
|
48
|
+
if Gem::Version.new(Gem::RubyGemsVersion) >= Gem::Version.new('1.2.0') then
|
49
|
+
s.add_runtime_dependency(%q<patron>, [">= 0.4.0"])
|
50
|
+
else
|
51
|
+
s.add_dependency(%q<patron>, [">= 0.4.0"])
|
52
|
+
end
|
53
|
+
else
|
54
|
+
s.add_dependency(%q<patron>, [">= 0.4.0"])
|
55
|
+
end
|
56
|
+
end
|
@@ -0,0 +1,27 @@
|
|
1
|
+
require File.join(File.dirname(__FILE__), 'test_helper.rb')
|
2
|
+
|
3
|
+
class ConfigurationTest < Test::Unit::TestCase
|
4
|
+
context "A RackspaceCloud configuration" do
|
5
|
+
setup do
|
6
|
+
@config = {:user => "foo", :access_key => "aabbccdd"}
|
7
|
+
end
|
8
|
+
|
9
|
+
should "contain a username" do
|
10
|
+
@config[:user] = nil
|
11
|
+
assert_raise(ArgumentError) {
|
12
|
+
RackspaceCloud::Base.new(@config)
|
13
|
+
}
|
14
|
+
end
|
15
|
+
|
16
|
+
should "contain an authorization token" do
|
17
|
+
@config[:access_key] = nil
|
18
|
+
assert_raise(ArgumentError) {
|
19
|
+
RackspaceCloud::Base.new(@config)
|
20
|
+
}
|
21
|
+
end
|
22
|
+
|
23
|
+
should "should be valid if all required parameters are specified" do
|
24
|
+
assert_nothing_raised { RackspaceCloud::Base.new(@config) }
|
25
|
+
end
|
26
|
+
end
|
27
|
+
end
|
data/test/test_helper.rb
ADDED
@@ -0,0 +1,11 @@
|
|
1
|
+
require 'rubygems'
|
2
|
+
require 'test/unit'
|
3
|
+
gem 'thoughtbot-shoulda'
|
4
|
+
|
5
|
+
begin
|
6
|
+
require 'shoulda'
|
7
|
+
rescue LoadError
|
8
|
+
abort "Unable to find thoughtbot-shoulda gem - please check that Shoulda is installed"
|
9
|
+
end
|
10
|
+
|
11
|
+
require File.join(File.dirname(__FILE__), '..', 'lib', 'rackspace_cloud')
|
metadata
ADDED
@@ -0,0 +1,81 @@
|
|
1
|
+
--- !ruby/object:Gem::Specification
|
2
|
+
name: rackspace_cloud
|
3
|
+
version: !ruby/object:Gem::Version
|
4
|
+
version: 0.4.0
|
5
|
+
platform: ruby
|
6
|
+
authors:
|
7
|
+
- Grant Goodale
|
8
|
+
autorequire:
|
9
|
+
bindir: bin
|
10
|
+
cert_chain: []
|
11
|
+
|
12
|
+
date: 2009-08-03 00:00:00 -07:00
|
13
|
+
default_executable:
|
14
|
+
dependencies:
|
15
|
+
- !ruby/object:Gem::Dependency
|
16
|
+
name: patron
|
17
|
+
type: :runtime
|
18
|
+
version_requirement:
|
19
|
+
version_requirements: !ruby/object:Gem::Requirement
|
20
|
+
requirements:
|
21
|
+
- - ">="
|
22
|
+
- !ruby/object:Gem::Version
|
23
|
+
version: 0.4.0
|
24
|
+
version:
|
25
|
+
description: Gem enabling the management of Rackspace Cloud Server instances.
|
26
|
+
email: grant@moreblinktag.com
|
27
|
+
executables: []
|
28
|
+
|
29
|
+
extensions: []
|
30
|
+
|
31
|
+
extra_rdoc_files:
|
32
|
+
- README
|
33
|
+
files:
|
34
|
+
- MIT-LICENSE
|
35
|
+
- README
|
36
|
+
- Rakefile
|
37
|
+
- VERSION
|
38
|
+
- init.rb
|
39
|
+
- install.rb
|
40
|
+
- lib/rackspace_cloud.rb
|
41
|
+
- lib/rackspace_cloud/base.rb
|
42
|
+
- lib/rackspace_cloud/flavor.rb
|
43
|
+
- lib/rackspace_cloud/image.rb
|
44
|
+
- lib/rackspace_cloud/server.rb
|
45
|
+
- lib/rackspace_cloud/shared_ip_group.rb
|
46
|
+
- rackspace_cloud.gemspec
|
47
|
+
- test/authentication_test.rb
|
48
|
+
- test/configuration_test.rb
|
49
|
+
- test/test_helper.rb
|
50
|
+
has_rdoc: true
|
51
|
+
homepage: http://github.com/ggoodale/rackspace_cloud
|
52
|
+
licenses: []
|
53
|
+
|
54
|
+
post_install_message:
|
55
|
+
rdoc_options:
|
56
|
+
- --charset=UTF-8
|
57
|
+
require_paths:
|
58
|
+
- lib
|
59
|
+
required_ruby_version: !ruby/object:Gem::Requirement
|
60
|
+
requirements:
|
61
|
+
- - ">="
|
62
|
+
- !ruby/object:Gem::Version
|
63
|
+
version: "0"
|
64
|
+
version:
|
65
|
+
required_rubygems_version: !ruby/object:Gem::Requirement
|
66
|
+
requirements:
|
67
|
+
- - ">="
|
68
|
+
- !ruby/object:Gem::Version
|
69
|
+
version: "0"
|
70
|
+
version:
|
71
|
+
requirements: []
|
72
|
+
|
73
|
+
rubyforge_project:
|
74
|
+
rubygems_version: 1.3.3
|
75
|
+
signing_key:
|
76
|
+
specification_version: 3
|
77
|
+
summary: Gem enabling the management of Rackspace Cloud Server instances
|
78
|
+
test_files:
|
79
|
+
- test/authentication_test.rb
|
80
|
+
- test/configuration_test.rb
|
81
|
+
- test/test_helper.rb
|