bguthrie-awsymandias 0.2.1 → 0.3.1

Sign up to get free protection for your applications and to get access to all the features.
Files changed (40) hide show
  1. data/.specification +57 -0
  2. data/README.rdoc +25 -21
  3. data/Rakefile +20 -4
  4. data/VERSION +1 -1
  5. data/awsymandias.gemspec +37 -12
  6. data/lib/awsymandias.rb +36 -331
  7. data/lib/awsymandias/addons/right_elb_interface.rb +375 -0
  8. data/lib/awsymandias/ec2.rb +49 -0
  9. data/lib/awsymandias/ec2/application_stack.rb +261 -0
  10. data/lib/awsymandias/extensions/class_extension.rb +18 -0
  11. data/lib/awsymandias/extensions/net_http_extension.rb +9 -0
  12. data/lib/awsymandias/instance.rb +149 -0
  13. data/lib/awsymandias/load_balancer.rb +157 -0
  14. data/lib/awsymandias/right_aws.rb +73 -0
  15. data/lib/awsymandias/right_elb.rb +16 -0
  16. data/lib/awsymandias/simple_db.rb +46 -0
  17. data/lib/awsymandias/snapshot.rb +33 -0
  18. data/lib/awsymandias/stack_definition.rb +60 -0
  19. data/lib/awsymandias/volume.rb +70 -0
  20. data/spec/integration/instance_spec.rb +37 -0
  21. data/spec/unit/addons/right_elb_interface_spec.rb +45 -0
  22. data/spec/unit/awsymandias_spec.rb +61 -0
  23. data/spec/unit/ec2/application_stack_spec.rb +634 -0
  24. data/spec/unit/instance_spec.rb +365 -0
  25. data/spec/unit/load_balancer_spec.rb +250 -0
  26. data/spec/unit/right_aws_spec.rb +90 -0
  27. data/spec/unit/simple_db_spec.rb +63 -0
  28. data/spec/unit/snapshot_spec.rb +39 -0
  29. data/spec/unit/stack_definition_spec.rb +113 -0
  30. data/tags +368 -0
  31. metadata +39 -13
  32. data/spec/awsymandias_spec.rb +0 -815
  33. data/vendor/aws-sdb/LICENSE +0 -19
  34. data/vendor/aws-sdb/README +0 -1
  35. data/vendor/aws-sdb/Rakefile +0 -20
  36. data/vendor/aws-sdb/lib/aws_sdb.rb +0 -3
  37. data/vendor/aws-sdb/lib/aws_sdb/error.rb +0 -42
  38. data/vendor/aws-sdb/lib/aws_sdb/service.rb +0 -191
  39. data/vendor/aws-sdb/spec/aws_sdb/service_spec.rb +0 -183
  40. data/vendor/aws-sdb/spec/spec_helper.rb +0 -4
@@ -1,19 +0,0 @@
1
- Copyright (c) 2007, 2008 Tim Dysinger
2
-
3
- Permission is hereby granted, free of charge, to any person obtaining a copy
4
- of this software and associated documentation files (the "Software"), to deal
5
- in the Software without restriction, including without limitation the rights
6
- to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
7
- copies of the Software, and to permit persons to whom the Software is
8
- furnished to do so, subject to the following conditions:
9
-
10
- The above copyright notice and this permission notice shall be included in
11
- all copies or substantial portions of the Software.
12
-
13
- THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
14
- IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
15
- FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
16
- AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
17
- LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
18
- OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
19
- THE SOFTWARE.
@@ -1 +0,0 @@
1
- Amazon SDB API
@@ -1,20 +0,0 @@
1
- require 'rubygems'
2
- require 'spec/rake/spectask'
3
- require 'rake/gempackagetask'
4
-
5
- Spec::Rake::SpecTask.new
6
-
7
- gem_spec = eval(IO.read(File.join(File.dirname(__FILE__), "aws-sdb.gemspec")))
8
-
9
- desc "Open an irb session preloaded with this library"
10
- task :console do
11
- sh "irb -rubygems -I lib -r aws_sdb.rb"
12
- end
13
-
14
- Rake::GemPackageTask.new(gem_spec) do |pkg|
15
- pkg.gem_spec = gem_spec
16
- end
17
-
18
- task :install => [:package] do
19
- sh %{sudo gem install pkg/#{gem_spec.name}-#{gem_spec.version}}
20
- end
@@ -1,3 +0,0 @@
1
- require 'aws_sdb/error'
2
- require 'aws_sdb/service'
3
-
@@ -1,42 +0,0 @@
1
- module AwsSdb
2
-
3
- class Error < RuntimeError ; end
4
-
5
- class RequestError < Error
6
- attr_reader :request_id
7
-
8
- def initialize(message, request_id=nil)
9
- super(message)
10
- @request_id = request_id
11
- end
12
- end
13
-
14
- class InvalidDomainNameError < RequestError ; end
15
- class InvalidParameterValueError < RequestError ; end
16
- class InvalidNextTokenError < RequestError ; end
17
- class InvalidNumberPredicatesError < RequestError ; end
18
- class InvalidNumberValueTestsError < RequestError ; end
19
- class InvalidQueryExpressionError < RequestError ; end
20
- class MissingParameterError < RequestError ; end
21
- class NoSuchDomainError < RequestError ; end
22
- class NumberDomainsExceededError < RequestError ; end
23
- class NumberDomainAttributesExceededError < RequestError ; end
24
- class NumberDomainBytesExceededError < RequestError ; end
25
- class NumberItemAttributesExceededError < RequestError ; end
26
- class RequestTimeoutError < RequestError ; end
27
-
28
- class FeatureDeprecatedError < RequestError ; end
29
-
30
- class ConnectionError < Error
31
- attr_reader :response
32
-
33
- def initialize(response)
34
- super(
35
- "#{response.code} \
36
- #{response.message if response.respond_to?(:message)}"
37
- )
38
- @response = response
39
- end
40
- end
41
-
42
- end
@@ -1,191 +0,0 @@
1
- require 'logger'
2
- require 'time'
3
- require 'cgi'
4
- require 'uri'
5
- require 'net/http'
6
- require 'base64'
7
- require 'openssl'
8
- require 'rexml/document'
9
- require 'rexml/xpath'
10
-
11
- module AwsSdb
12
-
13
- class Service
14
- def initialize(options={})
15
- @access_key_id = options[:access_key_id] || ENV['AMAZON_ACCESS_KEY_ID']
16
- @secret_access_key = options[:secret_access_key] || ENV['AMAZON_SECRET_ACCESS_KEY']
17
- @base_url = options[:url] || 'http://sdb.amazonaws.com'
18
- @logger = options[:logger] || Logger.new("aws_sdb.log")
19
- end
20
-
21
- def list_domains(max = nil, token = nil)
22
- params = { 'Action' => 'ListDomains' }
23
- params['NextToken'] =
24
- token unless token.nil? || token.empty?
25
- params['MaxNumberOfDomains'] =
26
- max.to_s unless max.nil? || max.to_i == 0
27
- doc = call(:get, params)
28
- results = []
29
- REXML::XPath.each(doc, '//DomainName/text()') do |domain|
30
- results << domain.to_s
31
- end
32
- return results, REXML::XPath.first(doc, '//NextToken/text()').to_s
33
- end
34
-
35
- def create_domain(domain)
36
- call(:post, { 'Action' => 'CreateDomain', 'DomainName'=> domain.to_s })
37
- nil
38
- end
39
-
40
- def delete_domain(domain)
41
- call(
42
- :delete,
43
- { 'Action' => 'DeleteDomain', 'DomainName' => domain.to_s }
44
- )
45
- nil
46
- end
47
- # <QueryWithAttributesResult><Item><Name>in-c2ffrw</Name><Attribute><Name>code</Name><Value>in-c2ffrw</Value></Attribute><Attribute><Name>date_created</Name><Value>2008-10-31</Value></Attribute></Item><Item>
48
- def query_with_attributes(domain, query, max = nil, token = nil)
49
- params = {
50
- 'Action' => 'QueryWithAttributes',
51
- 'QueryExpression' => query,
52
- 'DomainName' => domain.to_s
53
- }
54
- params['NextToken'] =
55
- token unless token.nil? || token.empty?
56
- params['MaxNumberOfItems'] =
57
- max.to_s unless max.nil? || max.to_i == 0
58
-
59
- doc = call(:get, params)
60
- results = []
61
- REXML::XPath.each(doc, "//Item") do |item|
62
- name = REXML::XPath.first(item, './Name/text()').to_s
63
-
64
-
65
- attributes = {'Name' => name}
66
- REXML::XPath.each(item, "./Attribute") do |attr|
67
- key = REXML::XPath.first(attr, './Name/text()').to_s
68
- value = REXML::XPath.first(attr, './Value/text()').to_s
69
- ( attributes[key] ||= [] ) << value
70
- end
71
- results << attributes
72
- end
73
- return results, REXML::XPath.first(doc, '//NextToken/text()').to_s
74
- end
75
-
76
- # <QueryResult><ItemName>in-c2ffrw</ItemName><ItemName>in-72yagt</ItemName><ItemName>in-52j8gj</ItemName>
77
- def query(domain, query, max = nil, token = nil)
78
- params = {
79
- 'Action' => 'Query',
80
- 'QueryExpression' => query,
81
- 'DomainName' => domain.to_s
82
- }
83
- params['NextToken'] =
84
- token unless token.nil? || token.empty?
85
- params['MaxNumberOfItems'] =
86
- max.to_s unless max.nil? || max.to_i == 0
87
-
88
-
89
- doc = call(:get, params)
90
- results = []
91
- REXML::XPath.each(doc, '//ItemName/text()') do |item|
92
- results << item.to_s
93
- end
94
- return results, REXML::XPath.first(doc, '//NextToken/text()').to_s
95
-
96
- end
97
-
98
- def put_attributes(domain, item, attributes, replace = true)
99
- params = {
100
- 'Action' => 'PutAttributes',
101
- 'DomainName' => domain.to_s,
102
- 'ItemName' => item.to_s
103
- }
104
- count = 0
105
- attributes.each do | key, values |
106
- ([]<<values).flatten.each do |value|
107
- params["Attribute.#{count}.Name"] = key.to_s
108
- params["Attribute.#{count}.Value"] = value.to_s
109
- params["Attribute.#{count}.Replace"] = replace
110
- count += 1
111
- end
112
- end
113
- call(:put, params)
114
- nil
115
- end
116
-
117
- def get_attributes(domain, item)
118
- doc = call(
119
- :get,
120
- {
121
- 'Action' => 'GetAttributes',
122
- 'DomainName' => domain.to_s,
123
- 'ItemName' => item.to_s
124
- }
125
- )
126
- attributes = {}
127
- REXML::XPath.each(doc, "//Attribute") do |attr|
128
- key = REXML::XPath.first(attr, './Name/text()').to_s
129
- value = REXML::XPath.first(attr, './Value/text()').to_s
130
- ( attributes[key] ||= [] ) << value
131
- end
132
- attributes
133
- end
134
-
135
- def delete_attributes(domain, item)
136
- call(
137
- :delete,
138
- {
139
- 'Action' => 'DeleteAttributes',
140
- 'DomainName' => domain.to_s,
141
- 'ItemName' => item.to_s
142
- }
143
- )
144
- nil
145
- end
146
-
147
- protected
148
-
149
- def call(method, params)
150
- params.merge!( {
151
- 'Version' => '2007-11-07',
152
- 'SignatureVersion' => '1',
153
- 'AWSAccessKeyId' => @access_key_id,
154
- 'Timestamp' => Time.now.gmtime.iso8601
155
- }
156
- )
157
- data = ''
158
- query = []
159
- params.keys.sort_by { |k| k.upcase }.each do |key|
160
- data << "#{key}#{params[key].to_s}"
161
- query << "#{key}=#{CGI::escape(params[key].to_s)}"
162
- end
163
- digest = OpenSSL::Digest::Digest.new('sha1')
164
- hmac = OpenSSL::HMAC.digest(digest, @secret_access_key, data)
165
- signature = Base64.encode64(hmac).strip
166
- query << "Signature=#{CGI::escape(signature)}"
167
- query = query.join('&')
168
- url = "#{@base_url}?#{query}"
169
- uri = URI.parse(url)
170
- @logger.debug("#{url}") if @logger
171
- response =
172
- Net::HTTP.new(uri.host, uri.port).send_request(method, uri.request_uri)
173
- @logger.debug("#{response.code}\n#{response.body}") if @logger
174
- raise(ConnectionError.new(response)) unless (200..400).include?(
175
- response.code.to_i
176
- )
177
- doc = REXML::Document.new(response.body)
178
- error = doc.get_elements('*/Errors/Error')[0]
179
- raise(
180
- Module.class_eval(
181
- "AwsSdb::#{error.get_elements('Code')[0].text}Error"
182
- ).new(
183
- error.get_elements('Message')[0].text,
184
- doc.get_elements('*/RequestID')[0].text
185
- )
186
- ) unless error.nil?
187
- doc
188
- end
189
- end
190
-
191
- end
@@ -1,183 +0,0 @@
1
- require File.dirname(__FILE__) + '/../spec_helper.rb'
2
-
3
- require 'digest/sha1'
4
- require 'net/http'
5
- require 'rexml/document'
6
-
7
- require 'rubygems'
8
- require 'uuidtools'
9
-
10
- include AwsSdb
11
-
12
- describe Service, "when creating a new domain" do
13
- before(:all) do
14
- @service = AwsSdb::Service.new
15
- @domain = "test-#{UUID.random_create.to_s}"
16
- domains = @service.list_domains[0]
17
- domains.each do |d|
18
- @service.delete_domain(d) if d =~ /^test/
19
- end
20
- end
21
-
22
- after(:all) do
23
- @service.delete_domain(@domain)
24
- end
25
-
26
- it "should not raise an error if a valid new domain name is given" do
27
- lambda {
28
- @service.create_domain("test-#{UUID.random_create.to_s}")
29
- }.should_not raise_error
30
- end
31
-
32
- it "should not raise an error if the domain name already exists" do
33
- domain = "test-#{UUID.random_create.to_s}"
34
- lambda {
35
- @service.create_domain(domain)
36
- @service.create_domain(domain)
37
- }.should_not raise_error
38
- end
39
-
40
- it "should raise an error if an a nil or '' domain name is given" do
41
- lambda {
42
- @service.create_domain('')
43
- }.should raise_error(InvalidParameterValueError)
44
- lambda {
45
- @service.create_domain(nil)
46
- }.should raise_error(InvalidParameterValueError)
47
- lambda {
48
- @service.create_domain(' ')
49
- }.should raise_error(InvalidParameterValueError)
50
- end
51
-
52
- it "should raise an error if the domain name length is < 3 or > 255" do
53
- lambda {
54
- @service.create_domain('xx')
55
- }.should raise_error(InvalidParameterValueError)
56
- lambda {
57
- @service.create_domain('x'*256)
58
- }.should raise_error(InvalidParameterValueError)
59
- end
60
-
61
- it "should only accept domain names with a-z, A-Z, 0-9, '_', '-', and '.' " do
62
- lambda {
63
- @service.create_domain('@$^*()')
64
- }.should raise_error(InvalidParameterValueError)
65
- end
66
-
67
- it "should only accept a maximum of 100 domain names"
68
-
69
- it "should not have to call amazon to determine domain name correctness"
70
- end
71
-
72
- describe Service, "when listing domains" do
73
- before(:all) do
74
- @service = AwsSdb::Service.new
75
- @domain = "test-#{UUID.random_create.to_s}"
76
- @service.list_domains[0].each do |d|
77
- @service.delete_domain(d) if d =~ /^test/
78
- end
79
- @service.create_domain(@domain)
80
- end
81
-
82
- after(:all) do
83
- @service.delete_domain(@domain)
84
- end
85
-
86
- it "should return a complete list" do
87
- result = nil
88
- lambda { result = @service.list_domains[0] }.should_not raise_error
89
- result.should_not be_nil
90
- result.should_not be_empty
91
- result.include?(@domain).should == true
92
- end
93
- end
94
-
95
- describe Service, "when deleting domains" do
96
- before(:all) do
97
- @service = AwsSdb::Service.new
98
- @domain = "test-#{UUID.random_create.to_s}"
99
- @service.list_domains[0].each do |d|
100
- @service.delete_domain(d) if d =~ /^test/
101
- end
102
- @service.create_domain(@domain)
103
- end
104
-
105
- after do
106
- @service.delete_domain(@domain)
107
- end
108
-
109
- it "should be able to delete an existing domain" do
110
- lambda { @service.delete_domain(@domain) }.should_not raise_error
111
- end
112
-
113
- it "should not raise an error trying to delete a non-existing domain" do
114
- lambda {
115
- @service.delete_domain(UUID.random_create.to_s)
116
- }.should_not raise_error
117
- end
118
- end
119
-
120
- describe Service, "when managing items" do
121
- before(:all) do
122
- @service = AwsSdb::Service.new
123
- @domain = "test-#{UUID.random_create.to_s}"
124
- @service.list_domains[0].each do |d|
125
- @service.delete_domain(d) if d =~ /^test/
126
- end
127
- @service.create_domain(@domain)
128
- @item = "test-#{UUID.random_create.to_s}"
129
- @attributes = {
130
- :question => 'What is the answer?',
131
- :answer => [ true, 'testing123', 4.2, 42, 420 ]
132
- }
133
- end
134
-
135
- after(:all) do
136
- @service.delete_domain(@domain)
137
- end
138
-
139
- it "should be able to put attributes" do
140
- lambda {
141
- @service.put_attributes(@domain, @item, @attributes)
142
- }.should_not raise_error
143
- end
144
-
145
- it "should be able to get attributes" do
146
- result = nil
147
- lambda {
148
- result = @service.get_attributes(@domain, @item)
149
- }.should_not raise_error
150
- result.should_not be_nil
151
- result.should_not be_empty
152
- result.has_key?('answer').should == true
153
- @attributes[:answer].each do |v|
154
- result['answer'].include?(v.to_s).should == true
155
- end
156
- end
157
-
158
- it "should be able to query" do
159
- result = nil
160
- lambda {
161
- result = @service.query(@domain, "[ 'answer' = '42' ]")[0]
162
- }.should_not raise_error
163
- result.should_not be_nil
164
- result.should_not be_empty
165
- result.should_not be_nil
166
- result.include?(@item).should == true
167
- end
168
-
169
- it "should be able to query with attributes"
170
-
171
- it "should be able to delete attributes" do
172
- lambda {
173
- @service.delete_attributes(@domain, @item)
174
- }.should_not raise_error
175
- end
176
- end
177
-
178
- # TODO Pull the specs from the amazon docs and write more rspec
179
- # 100 attributes per each call
180
- # 256 total attribute name-value pairs per item
181
- # 250 million attributes per domain
182
- # 10 GB of total user data storage per domain
183
- # ...etc...