waz-storage 1.2.0 → 1.3.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 (40) hide show
  1. data/.gitignore +9 -9
  2. data/CHANGELOG.rdoc +72 -72
  3. data/Gemfile +4 -4
  4. data/Gemfile.lock +46 -40
  5. data/LICENSE +18 -18
  6. data/README.rdoc +310 -310
  7. data/lib/waz-blobs.rb +4 -4
  8. data/lib/waz-queues.rb +6 -6
  9. data/lib/waz-storage.rb +39 -39
  10. data/lib/waz-tables.rb +4 -4
  11. data/lib/waz/blobs/blob_object.rb +122 -122
  12. data/lib/waz/blobs/container.rb +172 -161
  13. data/lib/waz/blobs/exceptions.rb +10 -10
  14. data/lib/waz/blobs/service.rb +181 -156
  15. data/lib/waz/queues/exceptions.rb +28 -28
  16. data/lib/waz/queues/message.rb +64 -64
  17. data/lib/waz/queues/queue.rb +164 -164
  18. data/lib/waz/queues/service.rb +105 -105
  19. data/lib/waz/storage/base.rb +70 -70
  20. data/lib/waz/storage/exceptions.rb +33 -33
  21. data/lib/waz/storage/validation_rules.rb +25 -25
  22. data/lib/waz/tables/edm_type_helper.rb +44 -44
  23. data/lib/waz/tables/exceptions.rb +44 -44
  24. data/lib/waz/tables/service.rb +178 -178
  25. data/lib/waz/tables/table.rb +74 -74
  26. data/lib/waz/tables/table_array.rb +10 -10
  27. data/rakefile +8 -21
  28. data/{tests → spec}/configuration.rb +22 -22
  29. data/{tests/waz/blobs/blob_object_test.rb → spec/waz/blobs/blob_object_spec.rb} +80 -80
  30. data/{tests/waz/blobs/container_test.rb → spec/waz/blobs/container_spec.rb} +175 -162
  31. data/{tests/waz/blobs/service_test.rb → spec/waz/blobs/service_spec.rb} +336 -282
  32. data/{tests/waz/queues/message_test.rb → spec/waz/queues/message_spec.rb} +32 -32
  33. data/{tests/waz/queues/queue_test.rb → spec/waz/queues/queue_spec.rb} +205 -205
  34. data/{tests/waz/queues/service_test.rb → spec/waz/queues/service_spec.rb} +298 -298
  35. data/{tests → spec}/waz/storage/base_tests.rb +81 -81
  36. data/{tests/waz/storage/shared_key_core_service_test.rb → spec/waz/storage/shared_key_core_service_spec.rb} +141 -141
  37. data/{tests/waz/tables/service_test.rb → spec/waz/tables/service_spec.rb} +613 -613
  38. data/{tests/waz/tables/table_test.rb → spec/waz/tables/table_spec.rb} +97 -97
  39. data/waz-storage.gemspec +29 -27
  40. metadata +47 -26
@@ -1,165 +1,165 @@
1
- module WAZ
2
- module Queues
3
- # This class represents a Queue on Windows Azure Queues API. These are the methods implemented from Microsoft's API description
4
- # available on MSDN at http://msdn.microsoft.com/en-us/library/dd179363.aspx
5
- #
6
- # # list available queues
7
- # WAZ::Queues::Queue.list
8
- #
9
- # # create a queue (here you can also send hashed metadata)
10
- # WAZ::Queues::Queue.create('test-queue')
11
- #
12
- # # get a specific queue
13
- # queue = WAZ::Queues::Queue.find('test-queue')
14
- #
15
- # # get queue properties (including default headers)
16
- # queue.metadata #=> hash containing beautified metadata (:x_ms_meta_name)
17
- #
18
- # # set queue properties (should follow x-ms-meta to be persisted)
19
- # # if you specify the optional parameter overwrite, existing metadata
20
- # # will be deleted else merged with new one.
21
- # queue.put_properties!(:x_ms_meta_MyProperty => "my value")
22
- #
23
- # # delete queue
24
- # queue.destroy!
25
- #
26
- # # clear queue contents
27
- # queue.clear
28
- #
29
- # # enqueue a message
30
- # queue.enqueue!("payload of the message")
31
- #
32
- # # peek a message/s (do not alter visibility, it can't be deleted neither)
33
- # # num_of_messages (1 to 32) to be peeked (default 1)
34
- # message = queue.peek
35
- #
36
- # # lock a message/s.
37
- # # num_of_messages (1 to 32) to be peeked (default 1)
38
- # # visiblity_timeout (default 60 sec. max 7200 [2hrs])
39
- # message = queue.lock
40
- #
41
- class Queue
42
- class << self
43
- # Returns an array of the queues (WAZ::Queues::Queue) existing on the current
44
- # Windows Azure Storage account.
45
- #
46
- # include_metadata defines if the metadata is retrieved along with queue data.
47
- def list(include_metadata = false)
48
- options = include_metadata ? { :include => 'metadata' } : {}
49
- service_instance.list_queues(options).map do |queue|
50
- WAZ::Queues::Queue.new(queue)
51
- end
52
- end
53
-
54
- # Creates a queue on the current account. If provided the metadata hash will specify additional
55
- # metadata to be stored on the queue. (Remember that metadata on the storage account must start with
56
- # :x_ms_metadata_{yourCustomPropertyName}, if not it will not be persisted).
57
- def create(queue_name, metadata = {})
58
- raise WAZ::Storage::InvalidParameterValue, {:name => "name", :values => ["lower letters, numbers or - (hypen), and must not start or end with - (hyphen)"]} unless WAZ::Storage::ValidationRules.valid_name?(queue_name)
59
- service_instance.create_queue(queue_name, metadata)
60
- WAZ::Queues::Queue.new(:name => queue_name, :url => service_instance.generate_request_uri(queue_name))
61
- end
62
-
63
- # Finds a queue by it's name, in case that it isn't found on the current storage account it will
64
- # return nil shilding the user from a ResourceNotFound exception.
65
- def find(queue_name)
66
- begin
67
- metadata = service_instance.get_queue_metadata(queue_name)
68
- WAZ::Queues::Queue.new(:name => queue_name, :url => service_instance.generate_request_uri(queue_name), :metadata => metadata)
69
- rescue RestClient::ResourceNotFound
70
- return nil
71
- end
72
- end
73
-
74
- # Syntax's sugar for find(:queue_name) or create(:queue_name)
75
- def ensure(queue_name)
76
- return (self.find(queue_name) or self.create(queue_name))
77
- end
78
-
79
- # This method is internally used by this class. It's the way we keep a single instance of the
80
- # service that wraps the calls the Windows Azure Queues API. It's initialized with the values
81
- # from the default_connection on WAZ::Storage::Base initialized thru establish_connection!
82
- def service_instance
83
- options = WAZ::Storage::Base.default_connection.merge(:type_of_service => "queue")
84
- (@service_instances ||= {})[options[:account_name]] ||= Service.new(options)
85
- end
86
- end
87
-
88
- attr_accessor :name, :url, :metadata
89
-
90
- def initialize(options = {})
91
- raise WAZ::Storage::InvalidOption, :name unless options.keys.include?(:name)
92
- raise WAZ::Storage::InvalidOption, :url unless options.keys.include?(:url)
93
- self.name = options[:name]
94
- self.url = options[:url]
95
- self.metadata = options[:metadata]
96
- end
97
-
98
- # Deletes the queue from the current storage account.
99
- def destroy!
100
- self.class.service_instance.delete_queue(self.name)
101
- end
102
-
103
- # Retrieves the metadata headers associated with the quere.
104
- def metadata
105
- metadata ||= self.class.service_instance.get_queue_metadata(self.name)
106
- end
107
-
108
- # Sets the metadata given on the new_metadata, when overwrite passed different
109
- # than true it overrides the metadata for the queue (removing all existing metadata)
110
- def put_properties!(new_metadata = {}, overwrite = false)
111
- new_metadata.merge!(metadata.reject { |k, v| !k.to_s.start_with? "x_ms_meta"} ) unless overwrite
112
- self.class.service_instance.set_queue_metadata(new_metadata)
113
- end
114
-
115
- # Enqueues a message on current queue. message is just a string that should be
116
- # UTF-8 serializable and ttl specifies the time-to-live of the message in the queue
117
- # (in seconds).
118
- def enqueue!(message, ttl = 604800)
119
- self.class.service_instance.enqueue(self.name, message, ttl)
120
- end
121
-
122
- # Returns the approximated queue size.
123
- def size
124
- metadata[:x_ms_approximate_messages_count].to_i
125
- end
126
-
127
- # Since Windows Azure Queues implement a Peek-Lock pattern
128
- # the method lock will lock a message preventing other users from
129
- # picking/locking the current message from the queue.
130
- #
131
- # The API supports multiple message processing by specifiying num_of_messages (up to 32)
132
- #
133
- # The visibility_timeout parameter (optional) specifies for how long the message will be
134
- # hidden from other users.
135
- def lock(num_of_messages = 1, visibility_timeout = nil)
136
- options = {}
137
- options[:num_of_messages] = num_of_messages
138
- options[:visiblity_timeout] = visibility_timeout unless visibility_timeout.nil?
139
- messages = self.class.service_instance.get_messages(self.name, options).map do |raw_message|
140
- WAZ::Queues::Message.new(raw_message.merge(:queue_name => self.name))
141
- end
142
- return messages.first() if num_of_messages == 1
143
- return messages
144
- end
145
-
146
- # Returns top N (default 1, up to 32) message from the queue without performing
147
- # any modification on the message. Since the message it's retrieved read-only
148
- # users cannot delete the peeked message.
149
- def peek(num_of_messages = 1)
150
- options = {}
151
- options[:num_of_messages] = num_of_messages
152
- messages = self.class.service_instance.peek(self.name, options).map do |raw_message|
153
- WAZ::Queues::Message.new(raw_message.merge(:queue_name => self.name))
154
- end
155
- return messages.first() if num_of_messages == 1
156
- return messages
157
- end
158
-
159
- # Marks every message on the queue for deletion (to be later garbage collected).
160
- def clear
161
- self.class.service_instance.clear_queue(self.name)
162
- end
163
- end
164
- end
1
+ module WAZ
2
+ module Queues
3
+ # This class represents a Queue on Windows Azure Queues API. These are the methods implemented from Microsoft's API description
4
+ # available on MSDN at http://msdn.microsoft.com/en-us/library/dd179363.aspx
5
+ #
6
+ # # list available queues
7
+ # WAZ::Queues::Queue.list
8
+ #
9
+ # # create a queue (here you can also send hashed metadata)
10
+ # WAZ::Queues::Queue.create('test-queue')
11
+ #
12
+ # # get a specific queue
13
+ # queue = WAZ::Queues::Queue.find('test-queue')
14
+ #
15
+ # # get queue properties (including default headers)
16
+ # queue.metadata #=> hash containing beautified metadata (:x_ms_meta_name)
17
+ #
18
+ # # set queue properties (should follow x-ms-meta to be persisted)
19
+ # # if you specify the optional parameter overwrite, existing metadata
20
+ # # will be deleted else merged with new one.
21
+ # queue.put_properties!(:x_ms_meta_MyProperty => "my value")
22
+ #
23
+ # # delete queue
24
+ # queue.destroy!
25
+ #
26
+ # # clear queue contents
27
+ # queue.clear
28
+ #
29
+ # # enqueue a message
30
+ # queue.enqueue!("payload of the message")
31
+ #
32
+ # # peek a message/s (do not alter visibility, it can't be deleted neither)
33
+ # # num_of_messages (1 to 32) to be peeked (default 1)
34
+ # message = queue.peek
35
+ #
36
+ # # lock a message/s.
37
+ # # num_of_messages (1 to 32) to be peeked (default 1)
38
+ # # visiblity_timeout (default 60 sec. max 7200 [2hrs])
39
+ # message = queue.lock
40
+ #
41
+ class Queue
42
+ class << self
43
+ # Returns an array of the queues (WAZ::Queues::Queue) existing on the current
44
+ # Windows Azure Storage account.
45
+ #
46
+ # include_metadata defines if the metadata is retrieved along with queue data.
47
+ def list(include_metadata = false)
48
+ options = include_metadata ? { :include => 'metadata' } : {}
49
+ service_instance.list_queues(options).map do |queue|
50
+ WAZ::Queues::Queue.new(queue)
51
+ end
52
+ end
53
+
54
+ # Creates a queue on the current account. If provided the metadata hash will specify additional
55
+ # metadata to be stored on the queue. (Remember that metadata on the storage account must start with
56
+ # :x_ms_metadata_{yourCustomPropertyName}, if not it will not be persisted).
57
+ def create(queue_name, metadata = {})
58
+ raise WAZ::Storage::InvalidParameterValue, {:name => "name", :values => ["lower letters, numbers or - (hypen), and must not start or end with - (hyphen)"]} unless WAZ::Storage::ValidationRules.valid_name?(queue_name)
59
+ service_instance.create_queue(queue_name, metadata)
60
+ WAZ::Queues::Queue.new(:name => queue_name, :url => service_instance.generate_request_uri(queue_name))
61
+ end
62
+
63
+ # Finds a queue by it's name, in case that it isn't found on the current storage account it will
64
+ # return nil shilding the user from a ResourceNotFound exception.
65
+ def find(queue_name)
66
+ begin
67
+ metadata = service_instance.get_queue_metadata(queue_name)
68
+ WAZ::Queues::Queue.new(:name => queue_name, :url => service_instance.generate_request_uri(queue_name), :metadata => metadata)
69
+ rescue RestClient::ResourceNotFound
70
+ return nil
71
+ end
72
+ end
73
+
74
+ # Syntax's sugar for find(:queue_name) or create(:queue_name)
75
+ def ensure(queue_name)
76
+ return (self.find(queue_name) or self.create(queue_name))
77
+ end
78
+
79
+ # This method is internally used by this class. It's the way we keep a single instance of the
80
+ # service that wraps the calls the Windows Azure Queues API. It's initialized with the values
81
+ # from the default_connection on WAZ::Storage::Base initialized thru establish_connection!
82
+ def service_instance
83
+ options = WAZ::Storage::Base.default_connection.merge(:type_of_service => "queue")
84
+ (@service_instances ||= {})[options[:account_name]] ||= Service.new(options)
85
+ end
86
+ end
87
+
88
+ attr_accessor :name, :url, :metadata
89
+
90
+ def initialize(options = {})
91
+ raise WAZ::Storage::InvalidOption, :name unless options.keys.include?(:name)
92
+ raise WAZ::Storage::InvalidOption, :url unless options.keys.include?(:url)
93
+ self.name = options[:name]
94
+ self.url = options[:url]
95
+ self.metadata = options[:metadata]
96
+ end
97
+
98
+ # Deletes the queue from the current storage account.
99
+ def destroy!
100
+ self.class.service_instance.delete_queue(self.name)
101
+ end
102
+
103
+ # Retrieves the metadata headers associated with the quere.
104
+ def metadata
105
+ metadata ||= self.class.service_instance.get_queue_metadata(self.name)
106
+ end
107
+
108
+ # Sets the metadata given on the new_metadata, when overwrite passed different
109
+ # than true it overrides the metadata for the queue (removing all existing metadata)
110
+ def put_properties!(new_metadata = {}, overwrite = false)
111
+ new_metadata.merge!(metadata.reject { |k, v| !k.to_s.start_with? "x_ms_meta"} ) unless overwrite
112
+ self.class.service_instance.set_queue_metadata(new_metadata)
113
+ end
114
+
115
+ # Enqueues a message on current queue. message is just a string that should be
116
+ # UTF-8 serializable and ttl specifies the time-to-live of the message in the queue
117
+ # (in seconds).
118
+ def enqueue!(message, ttl = 604800)
119
+ self.class.service_instance.enqueue(self.name, message, ttl)
120
+ end
121
+
122
+ # Returns the approximated queue size.
123
+ def size
124
+ metadata[:x_ms_approximate_messages_count].to_i
125
+ end
126
+
127
+ # Since Windows Azure Queues implement a Peek-Lock pattern
128
+ # the method lock will lock a message preventing other users from
129
+ # picking/locking the current message from the queue.
130
+ #
131
+ # The API supports multiple message processing by specifiying num_of_messages (up to 32)
132
+ #
133
+ # The visibility_timeout parameter (optional) specifies for how long the message will be
134
+ # hidden from other users.
135
+ def lock(num_of_messages = 1, visibility_timeout = nil)
136
+ options = {}
137
+ options[:num_of_messages] = num_of_messages
138
+ options[:visiblity_timeout] = visibility_timeout unless visibility_timeout.nil?
139
+ messages = self.class.service_instance.get_messages(self.name, options).map do |raw_message|
140
+ WAZ::Queues::Message.new(raw_message.merge(:queue_name => self.name))
141
+ end
142
+ return messages.first() if num_of_messages == 1
143
+ return messages
144
+ end
145
+
146
+ # Returns top N (default 1, up to 32) message from the queue without performing
147
+ # any modification on the message. Since the message it's retrieved read-only
148
+ # users cannot delete the peeked message.
149
+ def peek(num_of_messages = 1)
150
+ options = {}
151
+ options[:num_of_messages] = num_of_messages
152
+ messages = self.class.service_instance.peek(self.name, options).map do |raw_message|
153
+ WAZ::Queues::Message.new(raw_message.merge(:queue_name => self.name))
154
+ end
155
+ return messages.first() if num_of_messages == 1
156
+ return messages
157
+ end
158
+
159
+ # Marks every message on the queue for deletion (to be later garbage collected).
160
+ def clear
161
+ self.class.service_instance.clear_queue(self.name)
162
+ end
163
+ end
164
+ end
165
165
  end
@@ -1,106 +1,106 @@
1
- module WAZ
2
- module Queues
3
- # This is internally used by the waz-queues part of the gem and it exposes the Windows Azure Queue API REST methods
4
- # implementation. You can use this class to perform an specific operation that aren't provided by the current API.
5
- class Service
6
- include WAZ::Storage::SharedKeyCoreService
7
-
8
- # Lists the queues on the given storage account.
9
- #
10
- # When the options :include => 'metadata' is passed it returns
11
- # the corresponding metadata for each queue on the listing.
12
- def list_queues(options ={})
13
- content = execute(:get, nil, { :comp => 'list' }.merge!(options), { :x_ms_version => "2011-08-18" })
14
- doc = REXML::Document.new(content)
15
- queues = []
16
-
17
- REXML::XPath.each(doc, '//Queue/') do |item|
18
- metadata = {}
19
-
20
- item.elements['Metadata'].elements.each do |element|
21
- metadata.merge!(element.name.gsub(/-/, '_').downcase.to_sym => element.text)
22
- end unless item.elements['Metadata'].nil?
23
-
24
- queues << { :name => REXML::XPath.first(item, "Name").text,
25
- :url => REXML::XPath.first(item, "Url").text,
26
- :metadata => metadata}
27
- end
28
- return queues
29
- end
30
-
31
- # Creates a queue on the current storage account. Throws WAZ::Queues::QueueAlreadyExists when
32
- # existing metadata and given metadata differ.
33
- def create_queue(queue_name, metadata = {})
34
- execute(:put, queue_name, nil, metadata.merge!(:x_ms_version => '2011-08-18'))
35
- end
36
-
37
- # Deletes the given queue from the current storage account.
38
- def delete_queue(queue_name)
39
- execute(:delete, queue_name, {}, {:x_ms_version => '2011-08-18'})
40
- end
41
-
42
- # Gets the given queue metadata.
43
- def get_queue_metadata(queue_name)
44
- execute(:head, queue_name, { :comp => 'metadata'}, :x_ms_version => '2011-08-18').headers
45
- end
46
-
47
- # Sets the given queue metadata.
48
- def set_queue_metadata(queue_name, metadata = {})
49
- execute(:put, queue_name, { :comp => 'metadata' }, metadata.merge!(:x_ms_version => '2011-08-18'))
50
- end
51
-
52
- # Enqueues a message on the current queue.
53
- #
54
- # ttl Specifies the time-to-live interval for the message, in seconds. The maximum time-to-live allowed is 7 days. If this parameter
55
- # is omitted, the default time-to-live is 7 days.
56
- def enqueue(queue_name, message_payload, ttl = 604800)
57
- payload = "<?xml version=\"1.0\" encoding=\"utf-8\"?><QueueMessage><MessageText>#{message_payload}</MessageText></QueueMessage>"
58
- execute(:post, "#{queue_name}/messages", { :messagettl => ttl }, { 'Content-Type' => 'application/xml', :x_ms_version => "2011-08-18"}, payload)
59
- end
60
-
61
- # Locks N messages (1 default) from the given queue.
62
- #
63
- # :num_of_messages option specifies the max number of messages to get (maximum 32)
64
- #
65
- # :visibility_timeout option specifies the timeout of the message locking in seconds (max two hours)
66
- def get_messages(queue_name, options = {})
67
- raise WAZ::Queues::OptionOutOfRange, {:name => :num_of_messages, :min => 1, :max => 32} if (options.keys.include?(:num_of_messages) && (options[:num_of_messages].to_i < 1 || options[:num_of_messages].to_i > 32))
68
- raise WAZ::Queues::OptionOutOfRange, {:name => :visibility_timeout, :min => 1, :max => 7200} if (options.keys.include?(:visibility_timeout) && (options[:visibility_timeout].to_i < 1 || options[:visibility_timeout].to_i > 7200))
69
- content = execute(:get, "#{queue_name}/messages", options, {:x_ms_version => "2011-08-18"})
70
- doc = REXML::Document.new(content)
71
- messages = []
72
- REXML::XPath.each(doc, '//QueueMessage/') do |item|
73
- message = { :message_id => REXML::XPath.first(item, "MessageId").text,
74
- :message_text => REXML::XPath.first(item, "MessageText").text,
75
- :dequeue_count => REXML::XPath.first(item, "DequeueCount").nil? ? nil : REXML::XPath.first(item, "DequeueCount").text.to_i,
76
- :expiration_time => Time.httpdate(REXML::XPath.first(item, "ExpirationTime").text),
77
- :insertion_time => Time.httpdate(REXML::XPath.first(item, "InsertionTime").text) }
78
-
79
- # This are only valid when peek-locking messages
80
- message[:pop_receipt] = REXML::XPath.first(item, "PopReceipt").text unless REXML::XPath.first(item, "PopReceipt").nil?
81
- message[:time_next_visible] = Time.httpdate(REXML::XPath.first(item, "TimeNextVisible").text) unless REXML::XPath.first(item, "TimeNextVisible").nil?
82
- messages << message
83
- end
84
- return messages
85
- end
86
-
87
- # Peeks N messages (default 1) from the given queue.
88
- #
89
- # Implementation is the same of get_messages but differs on an additional parameter called :peek_only.
90
- def peek(queue_name, options = {})
91
- return get_messages(queue_name, {:peek_only => true}.merge(options))
92
- end
93
-
94
- # Deletes the given message from the queue, correlating the operation with the pop_receipt
95
- # in order to avoid eventually inconsistent scenarios.
96
- def delete_message(queue_name, message_id, pop_receipt)
97
- execute :delete, "#{queue_name}/messages/#{message_id}", { :pop_receipt => pop_receipt }
98
- end
99
-
100
- # Marks every message on the given queue for deletion.
101
- def clear_queue(queue_name)
102
- execute :delete, "#{queue_name}/messages", {}, :x_ms_version => '2011-08-18'
103
- end
104
- end
105
- end
1
+ module WAZ
2
+ module Queues
3
+ # This is internally used by the waz-queues part of the gem and it exposes the Windows Azure Queue API REST methods
4
+ # implementation. You can use this class to perform an specific operation that aren't provided by the current API.
5
+ class Service
6
+ include WAZ::Storage::SharedKeyCoreService
7
+
8
+ # Lists the queues on the given storage account.
9
+ #
10
+ # When the options :include => 'metadata' is passed it returns
11
+ # the corresponding metadata for each queue on the listing.
12
+ def list_queues(options ={})
13
+ content = execute(:get, nil, { :comp => 'list' }.merge!(options), { :x_ms_version => "2011-08-18" })
14
+ doc = REXML::Document.new(content)
15
+ queues = []
16
+
17
+ REXML::XPath.each(doc, '//Queue/') do |item|
18
+ metadata = {}
19
+
20
+ item.elements['Metadata'].elements.each do |element|
21
+ metadata.merge!(element.name.gsub(/-/, '_').downcase.to_sym => element.text)
22
+ end unless item.elements['Metadata'].nil?
23
+
24
+ queues << { :name => REXML::XPath.first(item, "Name").text,
25
+ :url => REXML::XPath.first(item, "Url").text,
26
+ :metadata => metadata}
27
+ end
28
+ return queues
29
+ end
30
+
31
+ # Creates a queue on the current storage account. Throws WAZ::Queues::QueueAlreadyExists when
32
+ # existing metadata and given metadata differ.
33
+ def create_queue(queue_name, metadata = {})
34
+ execute(:put, queue_name, nil, metadata.merge!(:x_ms_version => '2011-08-18'))
35
+ end
36
+
37
+ # Deletes the given queue from the current storage account.
38
+ def delete_queue(queue_name)
39
+ execute(:delete, queue_name, {}, {:x_ms_version => '2011-08-18'})
40
+ end
41
+
42
+ # Gets the given queue metadata.
43
+ def get_queue_metadata(queue_name)
44
+ execute(:head, queue_name, { :comp => 'metadata'}, :x_ms_version => '2011-08-18').headers
45
+ end
46
+
47
+ # Sets the given queue metadata.
48
+ def set_queue_metadata(queue_name, metadata = {})
49
+ execute(:put, queue_name, { :comp => 'metadata' }, metadata.merge!(:x_ms_version => '2011-08-18'))
50
+ end
51
+
52
+ # Enqueues a message on the current queue.
53
+ #
54
+ # ttl Specifies the time-to-live interval for the message, in seconds. The maximum time-to-live allowed is 7 days. If this parameter
55
+ # is omitted, the default time-to-live is 7 days.
56
+ def enqueue(queue_name, message_payload, ttl = 604800)
57
+ payload = "<?xml version=\"1.0\" encoding=\"utf-8\"?><QueueMessage><MessageText>#{message_payload}</MessageText></QueueMessage>"
58
+ execute(:post, "#{queue_name}/messages", { :messagettl => ttl }, { 'Content-Type' => 'application/xml', :x_ms_version => "2011-08-18"}, payload)
59
+ end
60
+
61
+ # Locks N messages (1 default) from the given queue.
62
+ #
63
+ # :num_of_messages option specifies the max number of messages to get (maximum 32)
64
+ #
65
+ # :visibility_timeout option specifies the timeout of the message locking in seconds (max two hours)
66
+ def get_messages(queue_name, options = {})
67
+ raise WAZ::Queues::OptionOutOfRange, {:name => :num_of_messages, :min => 1, :max => 32} if (options.keys.include?(:num_of_messages) && (options[:num_of_messages].to_i < 1 || options[:num_of_messages].to_i > 32))
68
+ raise WAZ::Queues::OptionOutOfRange, {:name => :visibility_timeout, :min => 1, :max => 7200} if (options.keys.include?(:visibility_timeout) && (options[:visibility_timeout].to_i < 1 || options[:visibility_timeout].to_i > 7200))
69
+ content = execute(:get, "#{queue_name}/messages", options, {:x_ms_version => "2011-08-18"})
70
+ doc = REXML::Document.new(content)
71
+ messages = []
72
+ REXML::XPath.each(doc, '//QueueMessage/') do |item|
73
+ message = { :message_id => REXML::XPath.first(item, "MessageId").text,
74
+ :message_text => REXML::XPath.first(item, "MessageText").text,
75
+ :dequeue_count => REXML::XPath.first(item, "DequeueCount").nil? ? nil : REXML::XPath.first(item, "DequeueCount").text.to_i,
76
+ :expiration_time => Time.httpdate(REXML::XPath.first(item, "ExpirationTime").text),
77
+ :insertion_time => Time.httpdate(REXML::XPath.first(item, "InsertionTime").text) }
78
+
79
+ # This are only valid when peek-locking messages
80
+ message[:pop_receipt] = REXML::XPath.first(item, "PopReceipt").text unless REXML::XPath.first(item, "PopReceipt").nil?
81
+ message[:time_next_visible] = Time.httpdate(REXML::XPath.first(item, "TimeNextVisible").text) unless REXML::XPath.first(item, "TimeNextVisible").nil?
82
+ messages << message
83
+ end
84
+ return messages
85
+ end
86
+
87
+ # Peeks N messages (default 1) from the given queue.
88
+ #
89
+ # Implementation is the same of get_messages but differs on an additional parameter called :peek_only.
90
+ def peek(queue_name, options = {})
91
+ return get_messages(queue_name, {:peek_only => true}.merge(options))
92
+ end
93
+
94
+ # Deletes the given message from the queue, correlating the operation with the pop_receipt
95
+ # in order to avoid eventually inconsistent scenarios.
96
+ def delete_message(queue_name, message_id, pop_receipt)
97
+ execute :delete, "#{queue_name}/messages/#{message_id}", { :pop_receipt => pop_receipt }
98
+ end
99
+
100
+ # Marks every message on the given queue for deletion.
101
+ def clear_queue(queue_name)
102
+ execute :delete, "#{queue_name}/messages", {}, :x_ms_version => '2011-08-18'
103
+ end
104
+ end
105
+ end
106
106
  end