bunny 0.6.3.rc2 → 0.7

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 (68) hide show
  1. data/.gitignore +8 -0
  2. data/.rspec +3 -0
  3. data/.travis.yml +15 -0
  4. data/.yardopts +9 -0
  5. data/CHANGELOG +3 -0
  6. data/Gemfile +39 -0
  7. data/Gemfile.lock +34 -0
  8. data/LICENSE +5 -4
  9. data/README.textile +54 -0
  10. data/Rakefile +15 -13
  11. data/bunny.gemspec +42 -61
  12. data/examples/simple_08.rb +4 -2
  13. data/examples/simple_09.rb +4 -2
  14. data/examples/simple_ack_08.rb +3 -1
  15. data/examples/simple_ack_09.rb +3 -1
  16. data/examples/simple_consumer_08.rb +4 -2
  17. data/examples/simple_consumer_09.rb +4 -2
  18. data/examples/simple_fanout_08.rb +3 -1
  19. data/examples/simple_fanout_09.rb +3 -1
  20. data/examples/simple_headers_08.rb +5 -3
  21. data/examples/simple_headers_09.rb +5 -3
  22. data/examples/simple_publisher_08.rb +3 -1
  23. data/examples/simple_publisher_09.rb +3 -1
  24. data/examples/simple_topic_08.rb +5 -3
  25. data/examples/simple_topic_09.rb +5 -3
  26. data/ext/amqp-0.8.json +616 -0
  27. data/ext/amqp-0.9.1.json +388 -0
  28. data/ext/config.yml +4 -0
  29. data/ext/qparser.rb +463 -0
  30. data/lib/bunny.rb +88 -66
  31. data/lib/bunny/channel08.rb +38 -38
  32. data/lib/bunny/channel09.rb +37 -37
  33. data/lib/bunny/client08.rb +184 -206
  34. data/lib/bunny/client09.rb +277 -363
  35. data/lib/bunny/consumer.rb +35 -0
  36. data/lib/bunny/exchange08.rb +37 -41
  37. data/lib/bunny/exchange09.rb +106 -124
  38. data/lib/bunny/queue08.rb +216 -202
  39. data/lib/bunny/queue09.rb +256 -326
  40. data/lib/bunny/subscription08.rb +30 -29
  41. data/lib/bunny/subscription09.rb +84 -83
  42. data/lib/bunny/version.rb +5 -0
  43. data/lib/qrack/amq-client-url.rb +165 -0
  44. data/lib/qrack/channel.rb +19 -17
  45. data/lib/qrack/client.rb +152 -151
  46. data/lib/qrack/errors.rb +5 -0
  47. data/lib/qrack/protocol/protocol08.rb +132 -130
  48. data/lib/qrack/protocol/protocol09.rb +133 -131
  49. data/lib/qrack/protocol/spec08.rb +2 -0
  50. data/lib/qrack/protocol/spec09.rb +2 -0
  51. data/lib/qrack/qrack08.rb +7 -10
  52. data/lib/qrack/qrack09.rb +7 -10
  53. data/lib/qrack/queue.rb +27 -40
  54. data/lib/qrack/subscription.rb +102 -101
  55. data/lib/qrack/transport/buffer08.rb +266 -264
  56. data/lib/qrack/transport/buffer09.rb +268 -264
  57. data/lib/qrack/transport/frame08.rb +13 -11
  58. data/lib/qrack/transport/frame09.rb +9 -7
  59. data/spec/spec_08/bunny_spec.rb +48 -45
  60. data/spec/spec_08/connection_spec.rb +10 -7
  61. data/spec/spec_08/exchange_spec.rb +145 -143
  62. data/spec/spec_08/queue_spec.rb +161 -161
  63. data/spec/spec_09/bunny_spec.rb +46 -44
  64. data/spec/spec_09/connection_spec.rb +15 -8
  65. data/spec/spec_09/exchange_spec.rb +147 -145
  66. data/spec/spec_09/queue_spec.rb +182 -184
  67. metadata +60 -41
  68. data/README.rdoc +0 -66
@@ -1,22 +1,16 @@
1
- module Bunny
2
-
3
- =begin rdoc
4
-
5
- === DESCRIPTION:
6
-
7
- Queues store and forward messages. Queues can be configured in the server or created at runtime.
8
- Queues must be attached to at least one exchange in order to receive messages from publishers.
1
+ # encoding: utf-8
9
2
 
10
- =end
3
+ module Bunny
11
4
 
12
- class Queue09 < Qrack::Queue
5
+ # Queues store and forward messages. Queues can be configured in the server or created at runtime.
6
+ # Queues must be attached to at least one exchange in order to receive messages from publishers.
7
+ class Queue09 < Qrack::Queue
8
+ def initialize(client, name, opts = {})
9
+ # check connection to server
10
+ raise Bunny::ConnectionError, 'Not connected to server' if client.status == :not_connected
13
11
 
14
- def initialize(client, name, opts = {})
15
- # check connection to server
16
- raise Bunny::ConnectionError, 'Not connected to server' if client.status == :not_connected
17
-
18
- @client = client
19
- @opts = opts
12
+ @client = client
13
+ @opts = opts
20
14
  @delivery_tag = nil
21
15
 
22
16
  # Queues without a given name are named by the server and are generally
@@ -27,369 +21,305 @@ Queues must be attached to at least one exchange in order to receive messages fr
27
21
  :durable => false,
28
22
  :exclusive => true,
29
23
  :auto_delete => true,
30
- :deprecated_ticket => 0
24
+ :deprecated_ticket => 0
31
25
  }.merge(opts)
32
26
  end
33
-
34
- # ignore the :nowait option if passed, otherwise program will hang waiting for a
35
- # response that will not be sent by the server
36
- opts.delete(:nowait)
37
-
38
- client.send_frame(
39
- Qrack::Protocol09::Queue::Declare.new({ :queue => name || '', :nowait => false, :deprecated_ticket => 0 }.merge(opts))
40
- )
41
-
42
- method = client.next_method
43
-
44
- client.check_response(method, Qrack::Protocol09::Queue::DeclareOk, "Error declaring queue #{name}")
45
-
46
- @name = method.queue
47
- client.queues[@name] = self
48
- end
49
-
50
- =begin rdoc
51
-
52
- === DESCRIPTION:
53
-
54
- Acknowledges one or more messages delivered via the _Deliver_ or _Get_-_Ok_ methods. The client can
55
- ask to confirm a single message or a set of messages up to and including a specific message.
56
-
57
- ==== OPTIONS:
58
-
59
- * <tt>:delivery_tag</tt>
60
- * <tt>:multiple => true or false (_default_)</tt> - If set to _true_, the delivery tag is treated
61
- as "up to and including", so that the client can acknowledge multiple messages with a single
62
- method. If set to _false_, the delivery tag refers to a single message. If the multiple field
63
- is _true_, and the delivery tag is zero, tells the server to acknowledge all outstanding messages.
64
-
65
- =end
66
-
67
- def ack(opts={})
68
- # Set delivery tag
69
- if delivery_tag.nil? and opts[:delivery_tag].nil?
70
- raise Bunny::AcknowledgementError, "No delivery tag received"
71
- else
72
- self.delivery_tag = opts[:delivery_tag] if delivery_tag.nil?
73
- end
74
-
75
- client.send_frame(
76
- Qrack::Protocol09::Basic::Ack.new({:delivery_tag => delivery_tag, :multiple => false}.merge(opts))
77
- )
78
-
79
- # reset delivery tag
80
- self.delivery_tag = nil
81
- end
82
-
83
- =begin rdoc
84
-
85
- === DESCRIPTION:
86
-
87
- Binds a queue to an exchange. Until a queue is bound it will not receive any messages. Queues are
88
- bound to the direct exchange '' by default. If error occurs, a _Bunny_::_ProtocolError_ is raised.
89
-
90
- * <tt>:key => 'routing key'* <tt>:key => 'routing_key'</tt> - Specifies the routing key for
91
- the binding. The routing key is used for routing messages depending on the exchange configuration.
92
- * <tt>:nowait => true or false (_default_)</tt> - Ignored by Bunny, always _false_.
93
-
94
- ==== RETURNS:
95
-
96
- <tt>:bind_ok</tt> if successful.
97
-
98
- =end
99
-
100
- def bind(exchange, opts = {})
101
- exchange = exchange.respond_to?(:name) ? exchange.name : exchange
102
-
103
- # ignore the :nowait option if passed, otherwise program will hang waiting for a
104
- # response that will not be sent by the server
105
- opts.delete(:nowait)
106
-
107
- client.send_frame(
108
- Qrack::Protocol09::Queue::Bind.new({ :queue => name,
109
- :exchange => exchange,
110
- :routing_key => opts.delete(:key),
111
- :nowait => false,
112
- :deprecated_ticket => 0 }.merge(opts))
113
- )
114
-
115
- method = client.next_method
116
-
117
- client.check_response(method, Qrack::Protocol09::Queue::BindOk,
118
- "Error binding queue: #{name} to exchange: #{exchange}")
119
-
120
- # return message
121
- :bind_ok
122
- end
123
-
124
- =begin rdoc
125
-
126
- === DESCRIPTION:
127
-
128
- Requests that a queue is deleted from broker/server. When a queue is deleted any pending messages
129
- are sent to a dead-letter queue if this is defined in the server configuration. Removes reference
130
- from queues if successful. If an error occurs raises _Bunny_::_ProtocolError_.
131
-
132
- ==== Options:
133
-
134
- * <tt>:if_unused => true or false (_default_)</tt> - If set to _true_, the server will only
135
- delete the queue if it has no consumers. If the queue has consumers the server does not
136
- delete it but raises a channel exception instead.
137
- * <tt>:if_empty => true or false (_default_)</tt> - If set to _true_, the server will only
138
- delete the queue if it has no messages. If the queue is not empty the server raises a channel
139
- exception.
140
- * <tt>:nowait => true or false (_default_)</tt> - Ignored by Bunny, always _false_.
141
-
142
- ==== Returns:
143
-
144
- <tt>:delete_ok</tt> if successful
145
- =end
146
-
147
- def delete(opts = {})
148
- # ignore the :nowait option if passed, otherwise program will hang waiting for a
149
- # response that will not be sent by the server
150
- opts.delete(:nowait)
151
-
152
- client.send_frame(
153
- Qrack::Protocol09::Queue::Delete.new({ :queue => name, :nowait => false, :deprecated_ticket => 0 }.merge(opts))
154
- )
155
-
156
- method = client.next_method
157
-
158
- client.check_response(method, Qrack::Protocol09::Queue::DeleteOk, "Error deleting queue #{name}")
159
-
160
- client.queues.delete(name)
161
27
 
162
- # return confirmation
163
- :delete_ok
164
- end
28
+ # ignore the :nowait option if passed, otherwise program will hang waiting for a
29
+ # response that will not be sent by the server
30
+ opts.delete(:nowait)
165
31
 
166
- =begin rdoc
32
+ opts = { :queue => name || '', :nowait => false, :deprecated_ticket => 0 }.merge(opts)
167
33
 
168
- === DESCRIPTION:
34
+ client.send_frame(Qrack::Protocol09::Queue::Declare.new(opts))
169
35
 
170
- Gets a message from a queue in a synchronous way. If error occurs, raises _Bunny_::_ProtocolError_.
171
-
172
- ==== OPTIONS:
173
-
174
- * <tt>:ack => false (_default_) or true</tt> - If set to _false_, the server does not expect an
175
- acknowledgement message from the client. If set to _true_, the server expects an acknowledgement
176
- message from the client and will re-queue the message if it does not receive one within a time specified
177
- by the server.
178
-
179
- ==== RETURNS:
180
-
181
- Hash <tt>{:header, :payload, :delivery_details}</tt>. <tt>:delivery_details</tt> is
182
- a hash <tt>{:consumer_tag, :delivery_tag, :redelivered, :exchange, :routing_key}</tt>.
183
-
184
- If the queue is empty the returned hash will contain the values -
185
-
186
- :header => nil
187
- :payload => :queue_empty
188
- :delivery_details => nil
189
-
190
- N.B. If a block is provided then the hash will be passed into the block and the return value
191
- will be nil.
192
-
193
- =end
36
+ method = client.next_method
194
37
 
195
- def pop(opts = {}, &blk)
196
-
197
- # do we want to have to provide an acknowledgement?
198
- ack = opts.delete(:ack)
199
-
200
- client.send_frame(
201
- Qrack::Protocol09::Basic::Get.new({ :queue => name,
202
- :consumer_tag => name,
203
- :no_ack => !ack,
204
- :nowait => true,
205
- :deprecated_ticket => 0 }.merge(opts))
206
- )
207
-
208
- method = client.next_method
209
-
210
- if method.is_a?(Qrack::Protocol09::Basic::GetEmpty) then
211
- queue_empty = true
212
- elsif !method.is_a?(Qrack::Protocol09::Basic::GetOk)
213
- raise Bunny::ProtocolError, "Error getting message from queue #{name}"
214
- end
38
+ client.check_response(method, Qrack::Protocol09::Queue::DeclareOk, "Error declaring queue #{name}")
215
39
 
216
- if !queue_empty
217
- # get delivery tag to use for acknowledge
218
- self.delivery_tag = method.delivery_tag if ack
40
+ @name = method.queue
41
+ client.queues[@name] = self
42
+ end
219
43
 
220
- header = client.next_payload
44
+ # @return [Bunny::Consumer] Default consumer associated with this queue (if any), or nil
45
+ # @note Default consumer is the one registered with the convenience {Bunny::Queue#subscribe} method. It has no special properties of any kind.
46
+ # @see Queue#subscribe
47
+ # @see Bunny::Consumer
48
+ # @api public
49
+ def default_consumer
50
+ @default_consumer
51
+ end
221
52
 
222
- # If maximum frame size is smaller than message payload body then message
223
- # will have a message header and several message bodies
224
- msg = ''
225
- while msg.length < header.size
226
- msg += client.next_payload
227
- end
53
+ # @return [Class]
54
+ # @private
55
+ def self.consumer_class
56
+ # Bunny::Consumer
57
+ Bunny::Subscription09
58
+ end # self.consumer_class
59
+
60
+ # Acknowledges one or more messages delivered via the _Deliver_ or _Get_-_Ok_ methods. The client can
61
+ # ask to confirm a single message or a set of messages up to and including a specific message.
62
+ #
63
+ # @option opts [String] :delivery_tag
64
+ #
65
+ # @option opts [Boolean] :multiple (false)
66
+ # If set to @true@, the delivery tag is treated as "up to and including",
67
+ # so that the client can acknowledge multiple messages with a single method.
68
+ # If set to @false@, the delivery tag refers to a single message.
69
+ # If the multiple field is @true@, and the delivery tag is zero,
70
+ # tells the server to acknowledge all outstanding messages.
71
+ def ack(opts = {})
72
+ # Set delivery tag
73
+ if delivery_tag.nil? and opts[:delivery_tag].nil?
74
+ raise Bunny::AcknowledgementError, "No delivery tag received"
75
+ else
76
+ self.delivery_tag = opts[:delivery_tag] if delivery_tag.nil?
77
+ end
228
78
 
229
- msg_hash = {:header => header, :payload => msg, :delivery_details => method.arguments}
79
+ opts = {:delivery_tag => delivery_tag, :multiple => false}.merge(opts)
230
80
 
231
- else
232
- msg_hash = {:header => nil, :payload => :queue_empty, :delivery_details => nil}
233
- end
81
+ client.send_frame(Qrack::Protocol09::Basic::Ack.new(opts))
234
82
 
235
- # Pass message hash to block or return message hash
236
- blk ? blk.call(msg_hash) : msg_hash
83
+ # reset delivery tag
84
+ self.delivery_tag = nil
85
+ end
237
86
 
238
- end
239
-
240
- =begin rdoc
87
+ # Binds a queue to an exchange. Until a queue is bound it won't receive
88
+ # any messages. Queues are bound to the direct exchange '' by default.
89
+ # If error occurs, a {Bunny::ProtocolError} is raised.
90
+ #
91
+ # @option opts [String] :key
92
+ # Specifies the routing key for the binding. The routing key is used
93
+ # for routing messages depending on the exchange configuration.
94
+ #
95
+ # @option opts [Boolean] :nowait (false)
96
+ # Ignored by Bunny, always @false@.
97
+ #
98
+ # @return [Symbol] @:bind_ok@ if successful.
99
+ def bind(exchange, opts = {})
100
+ exchange = exchange.respond_to?(:name) ? exchange.name : exchange
101
+
102
+ # ignore the :nowait option if passed, otherwise program will hang waiting for a
103
+ # response that will not be sent by the server
104
+ opts.delete(:nowait)
105
+
106
+ opts = {
107
+ :queue => name,
108
+ :exchange => exchange,
109
+ :routing_key => opts.delete(:key),
110
+ :nowait => false,
111
+ :deprecated_ticket => 0
112
+ }.merge(opts)
113
+
114
+ client.send_frame(Qrack::Protocol09::Queue::Bind.new(opts))
241
115
 
242
- === DESCRIPTION:
116
+ method = client.next_method
243
117
 
244
- Removes all messages from a queue. It does not cancel consumers. Purged messages are deleted
245
- without any formal "undo" mechanism. If an error occurs raises _Bunny_::_ProtocolError_.
118
+ client.check_response(method, Qrack::Protocol09::Queue::BindOk, "Error binding queue: #{name} to exchange: #{exchange}")
246
119
 
247
- ==== Options:
120
+ # return message
121
+ :bind_ok
122
+ end
248
123
 
249
- * <tt>:nowait => true or false (_default_)</tt> - Ignored by Bunny, always _false_.
124
+ # Requests that a queue is deleted from broker/server. When a queue is deleted any pending messages
125
+ # are sent to a dead-letter queue if this is defined in the server configuration. Removes reference
126
+ # from queues if successful. If an error occurs raises @Bunny::ProtocolError@.
127
+ #
128
+ # @option opts [Boolean] :if_unused (false)
129
+ # If set to @true@, the server will only delete the queue if it has no consumers.
130
+ # If the queue has consumers the server does not delete it but raises a channel exception instead.
131
+ #
132
+ # @option opts [Boolean] :if_empty (false)
133
+ # If set to @true@, the server will only delete the queue if it has no messages.
134
+ # If the queue is not empty the server raises a channel exception.
135
+ #
136
+ # @option opts [Boolean] :nowait (false)
137
+ # Ignored by Bunny, always @false@.
138
+ #
139
+ # @return [Symbol] @:delete_ok@ if successful
140
+ def delete(opts = {})
141
+ # ignore the :nowait option if passed, otherwise program will hang waiting for a
142
+ # response that will not be sent by the server
143
+ opts.delete(:nowait)
144
+
145
+ opts = { :queue => name, :nowait => false, :deprecated_ticket => 0 }.merge(opts)
146
+
147
+ client.send_frame(Qrack::Protocol09::Queue::Delete.new(opts))
250
148
 
251
- ==== Returns:
149
+ method = client.next_method
252
150
 
253
- <tt>:purge_ok</tt> if successful
254
- =end
151
+ client.check_response(method, Qrack::Protocol09::Queue::DeleteOk, "Error deleting queue #{name}")
255
152
 
256
- def purge(opts = {})
257
- # ignore the :nowait option if passed, otherwise program will hang waiting for a
258
- # response that will not be sent by the server
259
- opts.delete(:nowait)
153
+ client.queues.delete(name)
260
154
 
261
- client.send_frame(
262
- Qrack::Protocol09::Queue::Purge.new({ :queue => name, :nowait => false, :deprecated_ticket => 0 }.merge(opts))
263
- )
155
+ # return confirmation
156
+ :delete_ok
157
+ end
264
158
 
265
- method = client.next_method
159
+ # Gets a message from a queue in a synchronous way. If error occurs, raises _Bunny_::_ProtocolError_.
160
+ #
161
+ # @option opts [Boolean] :ack (false)
162
+ # If set to @false@, the server does not expect an acknowledgement message
163
+ # from the client. If set to @true@, the server expects an acknowledgement
164
+ # message from the client and will re-queue the message if it does not receive
165
+ # one within a time specified by the server.
166
+ #
167
+ # @return [Hash] Hash with @:header@, @:payload@ and @:delivery_details@ keys. @:delivery_details@ is a hash @:consumer_tag@, @:delivery_tag@, @:redelivered@, @:exchange@ and @:routing_key@. If the queue is empty the returned hash will contain: @{:header => nil, :payload => :queue_empty, :delivery_details => nil}@. N.B. If a block is provided then the hash will be passed into the block and the return value will be nil.
168
+ def pop(opts = {}, &blk)
169
+ opts = {
170
+ :queue => name,
171
+ :consumer_tag => name,
172
+ :no_ack => !opts[:ack],
173
+ :nowait => true,
174
+ :deprecated_ticket => 0
175
+ }.merge(opts)
176
+
177
+ client.send_frame(Qrack::Protocol09::Basic::Get.new(opts))
266
178
 
267
- client.check_response(method, Qrack::Protocol09::Queue::PurgeOk, "Error purging queue #{name}")
179
+ method = client.next_method
268
180
 
269
- # return confirmation
270
- :purge_ok
181
+ if method.is_a?(Qrack::Protocol09::Basic::GetEmpty) then
182
+ queue_empty = true
183
+ elsif !method.is_a?(Qrack::Protocol09::Basic::GetOk)
184
+ raise Bunny::ProtocolError, "Error getting message from queue #{name}"
185
+ end
271
186
 
272
- end
187
+ if !queue_empty
188
+ # get delivery tag to use for acknowledge
189
+ self.delivery_tag = method.delivery_tag if opts[:ack]
273
190
 
274
- =begin rdoc
191
+ header = client.next_payload
275
192
 
276
- === DESCRIPTION:
193
+ # If maximum frame size is smaller than message payload body then message
194
+ # will have a message header and several message bodies
195
+ msg = ''
196
+ while msg.length < header.size
197
+ msg << client.next_payload
198
+ end
277
199
 
278
- Returns hash {:message_count, :consumer_count}.
200
+ msg_hash = {:header => header, :payload => msg, :delivery_details => method.arguments}
279
201
 
280
- =end
281
-
282
- def status
283
- client.send_frame(
284
- Qrack::Protocol09::Queue::Declare.new({ :queue => name, :passive => true, :deprecated_ticket => 0 })
285
- )
286
- method = client.next_method
287
- {:message_count => method.message_count, :consumer_count => method.consumer_count}
288
- end
202
+ else
203
+ msg_hash = {:header => nil, :payload => :queue_empty, :delivery_details => nil}
204
+ end
289
205
 
290
- def subscribe(opts = {}, &blk)
291
- # Create subscription
292
- s = Bunny::Subscription09.new(client, self, opts)
293
- s.start(&blk)
294
-
295
- # Reset when subscription finished
296
- @subscription = nil
297
- end
298
-
299
- =begin rdoc
206
+ # Pass message hash to block or return message hash
207
+ blk ? blk.call(msg_hash) : msg_hash
208
+ end
300
209
 
301
- === DESCRIPTION:
210
+ # Removes all messages from a queue. It does not cancel consumers. Purged messages are deleted
211
+ # without any formal "undo" mechanism. If an error occurs raises {Bunny::ProtocolError}.
212
+ #
213
+ # @option opts [Boolean] :nowait (false)
214
+ # Ignored by Bunny, always @false@.
215
+ #
216
+ # @return [Symbol] @:purge_ok@ if successful
217
+ def purge(opts = {})
218
+ # ignore the :nowait option if passed, otherwise program will hang waiting for a
219
+ # response that will not be sent by the server
220
+ opts.delete(:nowait)
302
221
 
303
- Removes a queue binding from an exchange. If error occurs, a _Bunny_::_ProtocolError_ is raised.
222
+ opts = { :queue => name, :nowait => false, :deprecated_ticket => 0 }.merge(opts)
304
223
 
305
- ==== OPTIONS:
306
- * <tt>:key => 'routing key'* <tt>:key => 'routing_key'</tt> - Specifies the routing key for
307
- the binding.
308
- * <tt>:nowait => true or false (_default_)</tt> - Ignored by Bunny, always _false_.
224
+ client.send_frame(Qrack::Protocol09::Queue::Purge.new(opts))
309
225
 
310
- ==== RETURNS:
226
+ method = client.next_method
311
227
 
312
- <tt>:unbind_ok</tt> if successful.
228
+ client.check_response(method, Qrack::Protocol09::Queue::PurgeOk, "Error purging queue #{name}")
313
229
 
314
- =end
230
+ # return confirmation
231
+ :purge_ok
232
+ end
315
233
 
316
- def unbind(exchange, opts = {})
317
- exchange = exchange.respond_to?(:name) ? exchange.name : exchange
234
+ # @return [Hash] Hash with keys @:message_count@ and @consumer_count@.
235
+ def status
236
+ opts = { :queue => name, :passive => true, :deprecated_ticket => 0 }
237
+ client.send_frame(Qrack::Protocol09::Queue::Declare.new(opts))
318
238
 
319
- # ignore the :nowait option if passed, otherwise program will hang waiting for a
320
- # response that will not be sent by the server
321
- opts.delete(:nowait)
239
+ method = client.next_method
240
+ {:message_count => method.message_count, :consumer_count => method.consumer_count}
241
+ end
322
242
 
323
- client.send_frame(
324
- Qrack::Protocol09::Queue::Unbind.new({ :queue => name,
325
- :exchange => exchange,
326
- :routing_key => opts.delete(:key),
327
- :nowait => false,
328
- :deprecated_ticket => 0 }.merge(opts)
329
- )
330
- )
243
+ def subscribe(opts = {}, &blk)
244
+ raise RuntimeError.new("This queue already has default consumer. Please instantiate Bunny::Consumer directly and call its #consume method to register additional consumers.") if @default_consumer && ! opts[:consumer_tag]
331
245
 
332
- method = client.next_method
246
+ # Create a subscription.
247
+ @default_consumer = self.class.consumer_class.new(client, self, opts)
248
+ @default_consumer.consume(&blk)
249
+ end
333
250
 
334
- client.check_response(method, Qrack::Protocol09::Queue::UnbindOk, "Error unbinding queue #{name}")
251
+ # Removes a queue binding from an exchange. If error occurs, a _Bunny_::_ProtocolError_ is raised.
252
+ #
253
+ # @option opts [String] :key
254
+ # Specifies the routing key for the binding.
255
+ #
256
+ # @option opts [Boolean] :nowait (false)
257
+ # Ignored by Bunny, always @false@.
258
+ #
259
+ # @return [Symbol] @:unbind_ok@ if successful.
260
+ def unbind(exchange, opts = {})
261
+ exchange = exchange.respond_to?(:name) ? exchange.name : exchange
262
+
263
+ # ignore the :nowait option if passed, otherwise program will hang waiting for a
264
+ # response that will not be sent by the server
265
+ opts.delete(:nowait)
266
+
267
+ opts = {
268
+ :queue => name,
269
+ :exchange => exchange,
270
+ :routing_key => opts.delete(:key),
271
+ :nowait => false,
272
+ :deprecated_ticket => 0
273
+ }.merge(opts)
274
+
275
+ client.send_frame(Qrack::Protocol09::Queue::Unbind.new(opts))
335
276
 
336
- # return message
337
- :unbind_ok
338
- end
339
-
340
- =begin rdoc
277
+ method = client.next_method
341
278
 
342
- === DESCRIPTION:
279
+ client.check_response(method, Qrack::Protocol09::Queue::UnbindOk, "Error unbinding queue #{name}")
343
280
 
344
- Cancels a consumer. This does not affect already delivered messages, but it does mean
345
- the server will not send any more messages for that consumer.
281
+ # return message
282
+ :unbind_ok
283
+ end
346
284
 
347
- ==== OPTIONS:
285
+ # Cancels a consumer. This does not affect already delivered messages, but it does mean
286
+ # the server will not send any more messages for that consumer.
287
+ #
288
+ # @option opts [String] :consumer_tag
289
+ # Specifies the identifier for the consumer.
290
+ #
291
+ # @option opts [Boolean] :nowait (false)
292
+ # Ignored by Bunny, always @false@.
293
+ #
294
+ # @return [Symbol] @:unsubscribe_ok@ if successful
295
+ def unsubscribe(opts = {})
296
+ # Default consumer_tag from subscription if not passed in
297
+ consumer_tag = @default_consumer ? @default_consumer.consumer_tag : opts[:consumer_tag]
298
+
299
+ # Must have consumer tag to tell server what to unsubscribe
300
+ raise Bunny::UnsubscribeError,
301
+ "No consumer tag received" if !consumer_tag
348
302
 
349
- * <tt>:consumer_tag => '_tag_'</tt> - Specifies the identifier for the consumer.
350
- * <tt>:nowait => true or false (_default_)</tt> - Ignored by Bunny, always _false_.
303
+ # Cancel consumer
304
+ client.send_frame(Qrack::Protocol09::Basic::Cancel.new(:consumer_tag => consumer_tag, :nowait => false))
351
305
 
352
- ==== Returns:
306
+ method = client.next_method
353
307
 
354
- <tt>:unsubscribe_ok</tt> if successful
308
+ client.check_response(method, Qrack::Protocol09::Basic::CancelOk, "Error unsubscribing from queue #{name}")
355
309
 
356
- =end
357
-
358
- def unsubscribe(opts = {})
359
- # Default consumer_tag from subscription if not passed in
360
- consumer_tag = subscription ? subscription.consumer_tag : opts[:consumer_tag]
361
-
362
- # Must have consumer tag to tell server what to unsubscribe
363
- raise Bunny::UnsubscribeError,
364
- "No consumer tag received" if !consumer_tag
365
-
366
- # Cancel consumer
367
- client.send_frame( Qrack::Protocol09::Basic::Cancel.new(:consumer_tag => consumer_tag,
368
- :nowait => false))
310
+ # Reset subscription
311
+ @default_consumer = nil
369
312
 
370
- method = client.next_method
313
+ # Return confirmation
314
+ :unsubscribe_ok
315
+ end
371
316
 
372
- client.check_response(method, Qrack::Protocol09::Basic::CancelOk,
373
- "Error unsubscribing from queue #{name}")
317
+ private
374
318
 
375
- # Reset subscription
376
- @subscription = nil
377
-
378
- # Return confirmation
379
- :unsubscribe_ok
380
-
319
+ def exchange
320
+ @exchange ||= Bunny::Exchange09.new(client, '', :type => :direct, :key => name, :reserved_1 => 0, :reserved_2 => false, :reserved_3 => false)
381
321
  end
382
322
 
383
- private
384
-
385
- def exchange
386
- @exchange ||= Bunny::Exchange09.new(client, '', { :type => :direct,
387
- :key => name,
388
- :reserved_1 => 0,
389
- :reserved_2 => false,
390
- :reserved_3 => false})
391
- end
392
-
393
- end
394
-
323
+ end
324
+
395
325
  end