bunny 0.8.0 → 0.9.0.pre1

Sign up to get free protection for your applications and to get access to all the features.
Files changed (91) hide show
  1. data/.gitignore +7 -1
  2. data/.travis.yml +14 -4
  3. data/ChangeLog.md +72 -0
  4. data/Gemfile +17 -11
  5. data/README.md +82 -0
  6. data/bunny.gemspec +6 -13
  7. data/examples/connection/heartbeat.rb +17 -0
  8. data/lib/bunny.rb +40 -56
  9. data/lib/bunny/channel.rb +615 -19
  10. data/lib/bunny/channel_id_allocator.rb +59 -0
  11. data/lib/bunny/compatibility.rb +24 -0
  12. data/lib/bunny/concurrent/condition.rb +63 -0
  13. data/lib/bunny/consumer.rb +42 -26
  14. data/lib/bunny/consumer_tag_generator.rb +22 -0
  15. data/lib/bunny/consumer_work_pool.rb +67 -0
  16. data/lib/bunny/exceptions.rb +128 -0
  17. data/lib/bunny/exchange.rb +131 -136
  18. data/lib/bunny/framing.rb +53 -0
  19. data/lib/bunny/heartbeat_sender.rb +59 -0
  20. data/lib/bunny/main_loop.rb +70 -0
  21. data/lib/bunny/message_metadata.rb +126 -0
  22. data/lib/bunny/queue.rb +102 -275
  23. data/lib/bunny/session.rb +478 -0
  24. data/lib/bunny/socket.rb +44 -0
  25. data/lib/bunny/system_timer.rb +9 -9
  26. data/lib/bunny/transport.rb +179 -0
  27. data/lib/bunny/version.rb +1 -1
  28. data/spec/compatibility/queue_declare_spec.rb +40 -0
  29. data/spec/higher_level_api/integration/basic_ack_spec.rb +54 -0
  30. data/spec/higher_level_api/integration/basic_consume_spec.rb +51 -0
  31. data/spec/higher_level_api/integration/basic_get_spec.rb +47 -0
  32. data/spec/higher_level_api/integration/basic_nack_spec.rb +39 -0
  33. data/spec/higher_level_api/integration/basic_publish_spec.rb +105 -0
  34. data/spec/higher_level_api/integration/basic_qos_spec.rb +32 -0
  35. data/spec/higher_level_api/integration/basic_recover_spec.rb +18 -0
  36. data/spec/higher_level_api/integration/basic_reject_spec.rb +53 -0
  37. data/spec/higher_level_api/integration/basic_return_spec.rb +33 -0
  38. data/spec/higher_level_api/integration/channel_close_spec.rb +29 -0
  39. data/spec/higher_level_api/integration/channel_flow_spec.rb +24 -0
  40. data/spec/higher_level_api/integration/channel_open_spec.rb +57 -0
  41. data/spec/higher_level_api/integration/channel_open_stress_spec.rb +22 -0
  42. data/spec/higher_level_api/integration/confirm_select_spec.rb +19 -0
  43. data/spec/higher_level_api/integration/connection_spec.rb +340 -0
  44. data/spec/higher_level_api/integration/exchange_bind_spec.rb +31 -0
  45. data/spec/higher_level_api/integration/exchange_declare_spec.rb +183 -0
  46. data/spec/higher_level_api/integration/exchange_delete_spec.rb +37 -0
  47. data/spec/higher_level_api/integration/exchange_unbind_spec.rb +40 -0
  48. data/spec/higher_level_api/integration/queue_bind_spec.rb +109 -0
  49. data/spec/higher_level_api/integration/queue_declare_spec.rb +129 -0
  50. data/spec/higher_level_api/integration/queue_delete_spec.rb +38 -0
  51. data/spec/higher_level_api/integration/queue_purge_spec.rb +30 -0
  52. data/spec/higher_level_api/integration/queue_unbind_spec.rb +33 -0
  53. data/spec/higher_level_api/integration/tx_commit_spec.rb +21 -0
  54. data/spec/higher_level_api/integration/tx_rollback_spec.rb +21 -0
  55. data/spec/lower_level_api/integration/basic_cancel_spec.rb +57 -0
  56. data/spec/lower_level_api/integration/basic_consume_spec.rb +100 -0
  57. data/spec/spec_helper.rb +64 -0
  58. data/spec/unit/bunny_spec.rb +15 -0
  59. data/spec/unit/concurrent/condition_spec.rb +66 -0
  60. metadata +135 -93
  61. data/CHANGELOG +0 -21
  62. data/README.textile +0 -76
  63. data/Rakefile +0 -14
  64. data/examples/simple.rb +0 -32
  65. data/examples/simple_ack.rb +0 -35
  66. data/examples/simple_consumer.rb +0 -55
  67. data/examples/simple_fanout.rb +0 -41
  68. data/examples/simple_headers.rb +0 -42
  69. data/examples/simple_publisher.rb +0 -29
  70. data/examples/simple_topic.rb +0 -61
  71. data/ext/amqp-0.9.1.json +0 -389
  72. data/ext/config.yml +0 -4
  73. data/ext/qparser.rb +0 -426
  74. data/lib/bunny/client.rb +0 -370
  75. data/lib/bunny/subscription.rb +0 -92
  76. data/lib/qrack/amq-client-url.rb +0 -165
  77. data/lib/qrack/channel.rb +0 -20
  78. data/lib/qrack/client.rb +0 -247
  79. data/lib/qrack/errors.rb +0 -5
  80. data/lib/qrack/protocol/protocol.rb +0 -135
  81. data/lib/qrack/protocol/spec.rb +0 -525
  82. data/lib/qrack/qrack.rb +0 -20
  83. data/lib/qrack/queue.rb +0 -40
  84. data/lib/qrack/subscription.rb +0 -152
  85. data/lib/qrack/transport/buffer.rb +0 -305
  86. data/lib/qrack/transport/frame.rb +0 -102
  87. data/spec/spec_09/amqp_url_spec.rb +0 -19
  88. data/spec/spec_09/bunny_spec.rb +0 -76
  89. data/spec/spec_09/connection_spec.rb +0 -34
  90. data/spec/spec_09/exchange_spec.rb +0 -173
  91. data/spec/spec_09/queue_spec.rb +0 -240
@@ -0,0 +1,39 @@
1
+ require "spec_helper"
2
+
3
+ describe Bunny::Channel, "#nack" do
4
+ let(:connection) do
5
+ c = Bunny.new(:user => "bunny_gem", :password => "bunny_password", :vhost => "bunny_testbed")
6
+ c.start
7
+ c
8
+ end
9
+
10
+ after :all do
11
+ connection.close if connection.open?
12
+ end
13
+
14
+ subject do
15
+ connection.create_channel
16
+ end
17
+
18
+ context "with requeue = false" do
19
+ it "rejects a message" do
20
+ q = subject.queue("bunny.basic.nack.with-requeue-false", :exclusive => true)
21
+ x = subject.default_exchange
22
+
23
+ x.publish("bunneth", :routing_key => q.name)
24
+ sleep(0.5)
25
+ q.message_count.should == 1
26
+ delivery_info, _, content = q.pop(:ack => true)
27
+
28
+ subject.nack(delivery_info.delivery_tag, false, false)
29
+ sleep(0.5)
30
+ q.message_count.should == 0
31
+
32
+ subject.close
33
+ end
34
+ end
35
+
36
+ context "with multiple = true" do
37
+ it "rejects multiple messages"
38
+ end
39
+ end
@@ -0,0 +1,105 @@
1
+ require "spec_helper"
2
+
3
+ describe "Publishing a message to the default exchange" do
4
+ let(:connection) do
5
+ c = Bunny.new(:user => "bunny_gem", :password => "bunny_password", :vhost => "bunny_testbed")
6
+ c.start
7
+ c
8
+ end
9
+
10
+ after :all do
11
+ connection.close if connection.open?
12
+ end
13
+
14
+
15
+ context "with all default delivery and message properties" do
16
+ it "routes messages to a queue with the same name as the routing key" do
17
+ ch = connection.create_channel
18
+
19
+ q = ch.queue("", :exclusive => true)
20
+ x = ch.default_exchange
21
+
22
+ x.publish("xyzzy", :routing_key => q.name).
23
+ publish("xyzzy", :routing_key => q.name).
24
+ publish("xyzzy", :routing_key => q.name).
25
+ publish("xyzzy", :routing_key => q.name)
26
+
27
+ sleep(1)
28
+ q.message_count.should == 4
29
+
30
+ ch.close
31
+ end
32
+ end
33
+
34
+
35
+ context "with all default delivery and message properties" do
36
+ it "routes the messages and preserves all the metadata" do
37
+ ch = connection.create_channel
38
+
39
+ q = ch.queue("", :exclusive => true)
40
+ x = ch.default_exchange
41
+
42
+ x.publish("xyzzy", :routing_key => q.name, :persistent => true)
43
+
44
+ sleep(1)
45
+ q.message_count.should == 1
46
+
47
+ envelope, headers, payload = q.pop
48
+
49
+ payload.should == "xyzzy"
50
+
51
+ headers[:content_type].should == "application/octet-stream"
52
+ headers[:delivery_mode].should == 2
53
+ headers[:priority].should == 0
54
+
55
+ ch.close
56
+ end
57
+ end
58
+
59
+
60
+ context "with payload exceeding 128 Kb (max frame size)" do
61
+ it "successfully frames the message" do
62
+ ch = connection.create_channel
63
+
64
+ q = ch.queue("", :exclusive => true)
65
+ x = ch.default_exchange
66
+
67
+ as = ("a" * (1024 * 1024 * 4 + 28237777))
68
+ x.publish(as, :routing_key => q.name, :persistent => true)
69
+
70
+ sleep(1)
71
+ q.message_count.should == 1
72
+
73
+ _, _, payload = q.pop
74
+ payload.bytesize.should == as.bytesize
75
+
76
+ ch.close
77
+ end
78
+ end
79
+
80
+
81
+
82
+ context "with empty message body" do
83
+ it "successfully publishes the message" do
84
+ ch = connection.create_channel
85
+
86
+ q = ch.queue("", :exclusive => true)
87
+ x = ch.default_exchange
88
+
89
+ x.publish("", :routing_key => q.name, :persistent => true)
90
+
91
+ sleep(1)
92
+ q.message_count.should == 1
93
+
94
+ envelope, headers, payload = q.pop
95
+
96
+ payload.should == ""
97
+
98
+ headers[:content_type].should == "application/octet-stream"
99
+ headers[:delivery_mode].should == 2
100
+ headers[:priority].should == 0
101
+
102
+ ch.close
103
+ end
104
+ end
105
+ end
@@ -0,0 +1,32 @@
1
+ require "spec_helper"
2
+
3
+ describe Bunny::Channel, "#prefetch" do
4
+ let(:connection) do
5
+ c = Bunny.new(:user => "bunny_gem", :password => "bunny_password", :vhost => "bunny_testbed")
6
+ c.start
7
+ c
8
+ end
9
+
10
+ after :all do
11
+ connection.close
12
+ end
13
+
14
+
15
+ subject do
16
+ connection.create_channel
17
+ end
18
+
19
+ context "with a positive integer" do
20
+ it "sets that prefetch level via basic.qos" do
21
+ subject.prefetch(10).should be_instance_of(AMQ::Protocol::Basic::QosOk)
22
+ end
23
+ end
24
+
25
+ context "with a negative integer" do
26
+ it "raises an ArgumentError" do
27
+ expect {
28
+ subject.prefetch(-2)
29
+ }.to raise_error(ArgumentError)
30
+ end
31
+ end
32
+ end
@@ -0,0 +1,18 @@
1
+ require "spec_helper"
2
+
3
+ describe Bunny::Channel, "#recover" do
4
+ let(:connection) do
5
+ c = Bunny.new(:user => "bunny_gem", :password => "bunny_password", :vhost => "bunny_testbed")
6
+ c.start
7
+ c
8
+ end
9
+
10
+ subject do
11
+ connection.create_channel
12
+ end
13
+
14
+ it "is supported" do
15
+ subject.recover(true).should be_instance_of(AMQ::Protocol::Basic::RecoverOk)
16
+ subject.recover(true).should be_instance_of(AMQ::Protocol::Basic::RecoverOk)
17
+ end
18
+ end
@@ -0,0 +1,53 @@
1
+ require "spec_helper"
2
+
3
+ describe Bunny::Channel, "#reject" do
4
+ let(:connection) do
5
+ c = Bunny.new(:user => "bunny_gem", :password => "bunny_password", :vhost => "bunny_testbed")
6
+ c.start
7
+ c
8
+ end
9
+
10
+ after :all do
11
+ connection.close if connection.open?
12
+ end
13
+
14
+ subject do
15
+ connection.create_channel
16
+ end
17
+
18
+ context "with requeue = true" do
19
+ it "requeues a message" do
20
+ q = subject.queue("bunny.basic.reject.manual-acks", :exclusive => true)
21
+ x = subject.default_exchange
22
+
23
+ x.publish("bunneth", :routing_key => q.name)
24
+ sleep(0.5)
25
+ q.message_count.should == 1
26
+ delivery_info, _, _ = q.pop(:ack => true)
27
+
28
+ subject.reject(delivery_info.delivery_tag, true)
29
+ sleep(0.5)
30
+ q.message_count.should == 1
31
+
32
+ subject.close
33
+ end
34
+ end
35
+
36
+ context "with requeue = false" do
37
+ it "rejects a message" do
38
+ q = subject.queue("bunny.basic.reject.with-requeue-false", :exclusive => true)
39
+ x = subject.default_exchange
40
+
41
+ x.publish("bunneth", :routing_key => q.name)
42
+ sleep(0.5)
43
+ q.message_count.should == 1
44
+ delivery_info, _, _ = q.pop(:ack => true)
45
+
46
+ subject.reject(delivery_info.delivery_tag, false)
47
+ sleep(0.5)
48
+ q.message_count.should == 0
49
+
50
+ subject.close
51
+ end
52
+ end
53
+ end
@@ -0,0 +1,33 @@
1
+ require "spec_helper"
2
+
3
+ describe Bunny::Exchange, "#publish" do
4
+ let(:connection) do
5
+ c = Bunny.new(:user => "bunny_gem", :password => "bunny_password", :vhost => "bunny_testbed")
6
+ c.start
7
+ c
8
+ end
9
+
10
+ after :all do
11
+ connection.close if connection.open?
12
+ end
13
+
14
+
15
+ context "with :mandatory => true and a bad [no routes] routing key" do
16
+ it "causes a message to be returned" do
17
+ ch = connection.create_channel
18
+ x = ch.default_exchange
19
+
20
+ returned = []
21
+ x.on_return do |basic_deliver, properties, content|
22
+ returned << content
23
+ end
24
+
25
+ x.publish("xyzzy", :routing_key => rand.to_s, :mandatory => true)
26
+ sleep 0.5
27
+
28
+ returned.should include("xyzzy")
29
+
30
+ ch.close
31
+ end
32
+ end
33
+ end
@@ -0,0 +1,29 @@
1
+ require "spec_helper"
2
+
3
+ describe Bunny::Channel, "when closed" do
4
+ let(:connection) do
5
+ c = Bunny.new(:user => "bunny_gem", :password => "bunny_password", :vhost => "bunny_testbed")
6
+ c.start
7
+ c
8
+ end
9
+
10
+ after :all do
11
+ connection.close
12
+ end
13
+
14
+
15
+ subject do
16
+ connection.create_channel
17
+ end
18
+
19
+ it "releases the id" do
20
+ n = subject.number
21
+
22
+ subject.should be_open
23
+ subject.close
24
+ subject.should be_closed
25
+
26
+ # a new channel with the same id can be created
27
+ connection.create_channel(n)
28
+ end
29
+ end
@@ -0,0 +1,24 @@
1
+ require "spec_helper"
2
+
3
+ describe Bunny::Channel, "#flow" do
4
+ let(:connection) do
5
+ c = Bunny.new(:user => "bunny_gem", :password => "bunny_password", :vhost => "bunny_testbed")
6
+ c.start
7
+ c
8
+ end
9
+
10
+ after :all do
11
+ connection.close
12
+ end
13
+
14
+
15
+ subject do
16
+ connection.create_channel
17
+ end
18
+
19
+ it "is supported" do
20
+ subject.flow(true).should be_instance_of(AMQ::Protocol::Channel::FlowOk)
21
+ subject.flow(false).should be_instance_of(AMQ::Protocol::Channel::FlowOk)
22
+ subject.flow(true).should be_instance_of(AMQ::Protocol::Channel::FlowOk)
23
+ end
24
+ end
@@ -0,0 +1,57 @@
1
+ require "spec_helper"
2
+
3
+ describe Bunny::Channel, "when opened" do
4
+ let(:connection) do
5
+ c = Bunny.new(:user => "bunny_gem", :password => "bunny_password", :vhost => "bunny_testbed")
6
+ c.start
7
+ c
8
+ end
9
+
10
+ after :all do
11
+ connection.close
12
+ end
13
+
14
+ context "without explicitly provided id" do
15
+ subject do
16
+ connection.create_channel
17
+ end
18
+
19
+ it "gets an allocated id and is successfully opened" do
20
+ connection.should be_connected
21
+ subject.should be_open
22
+
23
+ subject.id.should be > 0
24
+ end
25
+ end
26
+
27
+
28
+ context "with explicitly provided id" do
29
+ subject do
30
+ connection.create_channel(767)
31
+ end
32
+
33
+ it "uses that id and is successfully opened" do
34
+ connection.should be_connected
35
+ subject.should be_open
36
+
37
+ subject.id.should == 767
38
+ end
39
+ end
40
+
41
+
42
+
43
+ context "with explicitly provided id that is already taken" do
44
+ subject do
45
+ connection.create_channel(767)
46
+ end
47
+
48
+ it "reuses the channel that is already opened" do
49
+ connection.should be_connected
50
+ subject.should be_open
51
+
52
+ subject.id.should == 767
53
+
54
+ connection.create_channel(767).should == subject
55
+ end
56
+ end
57
+ end
@@ -0,0 +1,22 @@
1
+ require "spec_helper"
2
+
3
+ describe "Rapidly opening and closing lots of channels" do
4
+ let(:connection) do
5
+ c = Bunny.new(:user => "bunny_gem", :password => "bunny_password", :vhost => "bunny_testbed")
6
+ c.start
7
+ c
8
+ end
9
+
10
+ after :all do
11
+ connection.close
12
+ end
13
+
14
+ it "works correctly" do
15
+ xs = Array.new(2000) { connection.create_channel }
16
+
17
+ xs.size.should == 2000
18
+ xs.each do |ch|
19
+ ch.close
20
+ end
21
+ end
22
+ end
@@ -0,0 +1,19 @@
1
+ require "spec_helper"
2
+
3
+ describe Bunny::Channel, "#confirm_select" do
4
+ let(:connection) do
5
+ c = Bunny.new(:user => "bunny_gem", :password => "bunny_password", :vhost => "bunny_testbed")
6
+ c.start
7
+ c
8
+ end
9
+
10
+ after :all do
11
+ connection.close if connection.open?
12
+ end
13
+
14
+ it "is supported" do
15
+ connection.with_channel do |ch|
16
+ ch.confirm_select
17
+ end
18
+ end
19
+ end
@@ -0,0 +1,340 @@
1
+ require "spec_helper"
2
+
3
+ describe Bunny::Session do
4
+ let(:port) { AMQ::Protocol::DEFAULT_PORT }
5
+ let(:username) { "guest" }
6
+
7
+ let(:tls_port) { AMQ::Protocol::TLS_PORT }
8
+
9
+ context "initialized via connection URI" do
10
+ after :each do
11
+ subject.close if subject.open?
12
+ end
13
+
14
+ context "when schema is not one of [amqp, amqps]" do
15
+ it "raises ArgumentError" do
16
+ expect {
17
+ described_class.new("http://dev.rabbitmq.com")
18
+ }.to raise_error(ArgumentError, /amqp or amqps schema/)
19
+ end
20
+ end
21
+
22
+
23
+ it "handles amqp:// URIs w/o path part" do
24
+ session = described_class.new("amqp://dev.rabbitmq.com")
25
+ session.start
26
+
27
+ session.vhost.should == "/"
28
+ session.host.should == "dev.rabbitmq.com"
29
+ session.port.should == 5672
30
+ session.ssl?.should be_false
31
+
32
+ session.close
33
+ end
34
+
35
+
36
+ context "when URI ends in a slash" do
37
+ it "parses vhost as an empty string" do
38
+ session = described_class.new("amqp://dev.rabbitmq.com/")
39
+
40
+ session.hostname.should == "dev.rabbitmq.com"
41
+ session.port.should == 5672
42
+ session.vhost.should == ""
43
+ end
44
+ end
45
+
46
+ context "when URI is amqp://dev.rabbitmq.com/a/path/with/slashes" do
47
+ it "raises an ArgumentError" do
48
+ lambda { described_class.new("amqp://dev.rabbitmq.com/a/path/with/slashes") }.should raise_error(ArgumentError)
49
+ end
50
+ end
51
+ end
52
+
53
+
54
+
55
+
56
+ context "initialized with all defaults" do
57
+ after :each do
58
+ subject.close if subject.open?
59
+ end
60
+
61
+ subject do
62
+ Bunny.new
63
+ end
64
+
65
+ it "successfully negotiates the connection" do
66
+ subject.start
67
+ subject.should be_connected
68
+
69
+ subject.server_properties.should_not be_nil
70
+ subject.server_capabilities.should_not be_nil
71
+
72
+ props = subject.server_properties
73
+
74
+ props["product"].should_not be_nil
75
+ props["platform"].should_not be_nil
76
+ props["version"].should_not be_nil
77
+ end
78
+ end
79
+
80
+ context "initialized with TCP connection timeout = 5" do
81
+ after :each do
82
+ subject.close if subject.open?
83
+ end
84
+
85
+ subject do
86
+ described_class.new(:connection_timeout => 5)
87
+ end
88
+
89
+ it "successfully connects" do
90
+ subject.start
91
+ subject.should be_connected
92
+
93
+ subject.server_properties.should_not be_nil
94
+ subject.server_capabilities.should_not be_nil
95
+
96
+ props = subject.server_properties
97
+
98
+ props["product"].should_not be_nil
99
+ props["platform"].should_not be_nil
100
+ props["version"].should_not be_nil
101
+ end
102
+ end
103
+
104
+ context "initialized with :host => 127.0.0.1" do
105
+ after :each do
106
+ subject.close if subject.open?
107
+ end
108
+
109
+ let(:host) { "127.0.0.1" }
110
+ subject do
111
+ described_class.new(:host => host)
112
+ end
113
+
114
+ it "uses hostname = 127.0.0.1" do
115
+ subject.host.should == host
116
+ subject.hostname.should == host
117
+ end
118
+
119
+ it "uses port 5672" do
120
+ subject.port.should == port
121
+ end
122
+
123
+ it "uses username = guest" do
124
+ subject.username.should == username
125
+ end
126
+ end
127
+
128
+ context "initialized with :hostname => localhost" do
129
+ after :each do
130
+ subject.close if subject.open?
131
+ end
132
+
133
+ let(:host) { "localhost" }
134
+ let(:subject) { described_class.new(:hostname => host) }
135
+
136
+ it "uses hostname = localhost" do
137
+ subject.host.should == host
138
+ subject.hostname.should == host
139
+ end
140
+
141
+ it "uses port 5672" do
142
+ subject.port.should == port
143
+ end
144
+
145
+ it "uses username = guest" do
146
+ subject.username.should == username
147
+ subject.user.should == username
148
+ end
149
+ end
150
+
151
+ context "initialized with :ssl => true" do
152
+ after :each do
153
+ subject.close if subject.open?
154
+ end
155
+
156
+ let(:subject) { described_class.new(:ssl => true) }
157
+
158
+ it "uses TLS port" do
159
+ subject.port.should == tls_port
160
+ end
161
+ end
162
+
163
+ context "initialized with :tls => true" do
164
+ after :each do
165
+ subject.close if subject.open?
166
+ end
167
+
168
+ let(:subject) { described_class.new(:tls => true) }
169
+
170
+ it "uses TLS port" do
171
+ subject.port.should == tls_port
172
+ end
173
+ end
174
+
175
+
176
+ context "initialized with :host => 127.0.0.1 and non-default credentials" do
177
+ after :each do
178
+ subject.close if subject.open?
179
+ end
180
+
181
+ let(:host) { "127.0.0.1" }
182
+ # see ./bin/ci/before_build.sh
183
+ let(:username) { "bunny_gem" }
184
+ let(:password) { "bunny_password" }
185
+ let(:vhost) { "bunny_testbed" }
186
+
187
+ subject do
188
+ described_class.new(:hostname => host, :username => username, :password => password, :virtual_host => vhost)
189
+ end
190
+
191
+ it "successfully connects" do
192
+ subject.start
193
+ subject.should be_connected
194
+
195
+ subject.server_properties.should_not be_nil
196
+ subject.server_capabilities.should_not be_nil
197
+
198
+ props = subject.server_properties
199
+
200
+ props["product"].should_not be_nil
201
+ props["platform"].should_not be_nil
202
+ props["version"].should_not be_nil
203
+ end
204
+
205
+ it "uses hostname = 127.0.0.1" do
206
+ subject.host.should == host
207
+ subject.hostname.should == host
208
+ end
209
+
210
+ it "uses port 5672" do
211
+ subject.port.should == port
212
+ end
213
+
214
+ it "uses provided vhost" do
215
+ subject.vhost.should == vhost
216
+ subject.virtual_host.should == vhost
217
+ end
218
+
219
+ it "uses provided username" do
220
+ subject.username.should == username
221
+ end
222
+
223
+ it "uses provided password" do
224
+ subject.password.should == password
225
+ end
226
+ end
227
+
228
+
229
+ context "initialized with :host => 127.0.0.1 and non-default credentials (take 2)" do
230
+ after :each do
231
+ subject.close if subject.open?
232
+ end
233
+
234
+ let(:host) { "127.0.0.1" }
235
+ # see ./bin/ci/before_build.sh
236
+ let(:username) { "bunny_gem" }
237
+ let(:password) { "bunny_password" }
238
+ let(:vhost) { "bunny_testbed" }
239
+
240
+ subject do
241
+ described_class.new(:hostname => host, :user => username, :pass => password, :vhost => vhost)
242
+ end
243
+
244
+ it "successfully connects" do
245
+ subject.start
246
+ subject.should be_connected
247
+
248
+ subject.server_properties.should_not be_nil
249
+ subject.server_capabilities.should_not be_nil
250
+
251
+ props = subject.server_properties
252
+
253
+ props["product"].should_not be_nil
254
+ props["platform"].should_not be_nil
255
+ props["version"].should_not be_nil
256
+ end
257
+
258
+ it "uses hostname = 127.0.0.1" do
259
+ subject.host.should == host
260
+ subject.hostname.should == host
261
+ end
262
+
263
+ it "uses port 5672" do
264
+ subject.port.should == port
265
+ end
266
+
267
+ it "uses provided username" do
268
+ subject.username.should == username
269
+ end
270
+
271
+ it "uses provided password" do
272
+ subject.password.should == password
273
+ end
274
+ end
275
+
276
+
277
+
278
+ context "initialized with :host => 127.0.0.1 and non-default credentials (take 2)" do
279
+ after :each do
280
+ subject.close if subject.open?
281
+ end
282
+
283
+ let(:host) { "127.0.0.1" }
284
+ # see ./bin/ci/before_build.sh
285
+ let(:username) { "bunny_gem" }
286
+ let(:password) { "bunny_password" }
287
+ let(:vhost) { "bunny_testbed" }
288
+ let(:interval) { 1 }
289
+
290
+ subject do
291
+ described_class.new(:hostname => host, :user => username, :pass => password, :vhost => vhost, :heartbeat_interval => interval)
292
+ end
293
+
294
+ it "successfully connects" do
295
+ subject.start
296
+ subject.should be_connected
297
+
298
+ subject.server_properties.should_not be_nil
299
+ subject.server_capabilities.should_not be_nil
300
+
301
+ props = subject.server_properties
302
+
303
+ props["product"].should_not be_nil
304
+ props["platform"].should_not be_nil
305
+ props["version"].should_not be_nil
306
+ end
307
+
308
+ it "uses provided heartbeat interval" do
309
+ subject.heartbeat.should == interval
310
+ end
311
+ end
312
+
313
+
314
+
315
+ context "initialized with :host => 127.0.0.1 and INVALID credentials" do
316
+ let(:host) { "127.0.0.1" }
317
+ # see ./bin/ci/before_build.sh
318
+ let(:username) { "bunny_gem#{Time.now.to_i}" }
319
+ let(:password) { "sdjkfhsdf8ysd8fy8" }
320
+ let(:vhost) { "___sd89aysd98789" }
321
+
322
+ subject do
323
+ described_class.new(:hostname => host, :user => username, :pass => password, :vhost => vhost)
324
+ end
325
+
326
+ it "fails to connect" do
327
+ lambda do
328
+ subject.start
329
+ end.should raise_error(Bunny::PossibleAuthenticationFailureError)
330
+ end
331
+
332
+ it "uses provided username" do
333
+ subject.username.should == username
334
+ end
335
+
336
+ it "uses provided password" do
337
+ subject.password.should == password
338
+ end
339
+ end
340
+ end