stomp 1.2.11 → 1.2.12
Sign up to get free protection for your applications and to get access to all the features.
- data/CHANGELOG.rdoc +12 -0
- data/README.rdoc +4 -0
- data/examples/slogger.rb +3 -3
- data/lib/client/utils.rb +50 -57
- data/lib/connection/heartbeats.rb +17 -10
- data/lib/connection/netio.rb +1 -1
- data/lib/connection/utils.rb +3 -0
- data/lib/stomp/client.rb +1 -0
- data/lib/stomp/connection.rb +14 -1
- data/lib/stomp/constants.rb +7 -0
- data/lib/stomp/errors.rb +8 -0
- data/lib/stomp/version.rb +1 -1
- data/notes/heartbeat_readme.txt +68 -2
- data/spec/client_spec.rb +2 -2
- data/spec/connection_spec.rb +18 -5
- data/stomp.gemspec +4 -2
- data/test/test_connection.rb +3 -2
- data/test/test_helper.rb +6 -1
- data/test/test_urlogin.rb +86 -0
- data/test/tlogger.rb +2 -2
- metadata +6 -4
data/CHANGELOG.rdoc
CHANGED
@@ -1,3 +1,15 @@
|
|
1
|
+
== 1.2.12 20130728
|
2
|
+
|
3
|
+
* Fix infinite loop when max reconn attempts is reached
|
4
|
+
* Enhance JRuby support in tests
|
5
|
+
* Issue #63, nil message on rapid AMQ restarts
|
6
|
+
* Issue #63, fast spurious failovers with JRuby and AMQ
|
7
|
+
* Issue #67, SSL SNI support (thanks Hiram)
|
8
|
+
* Proper cleanup when not reliable adn EOF from broker
|
9
|
+
* Remove extraneous privte declarations
|
10
|
+
* Issue #65, allow non-word characters in login and passcode using stomp://
|
11
|
+
* Issue #66, allow a single broker in a failover URL
|
12
|
+
|
1
13
|
== 1.2.11 20130728
|
2
14
|
|
3
15
|
* Issue #60, timeout/hang under JRuby
|
data/README.rdoc
CHANGED
@@ -12,6 +12,7 @@ An implementation of the Stomp protocol for Ruby. See:
|
|
12
12
|
|
13
13
|
See _CHANGELOG.rdoc_ for details.
|
14
14
|
|
15
|
+
* Gem version 1.2.12. Miscellaneous issue fixes and cleanup.
|
15
16
|
* Gem version 1.2.11. JRuby and AMQ support fixes.
|
16
17
|
* Gem version 1.2.10. Support failover from heartbeat threads.
|
17
18
|
* Gem version 1.2.9. Miscellaneous fixes and changes.
|
@@ -54,6 +55,9 @@ See _CHANGELOG.rdoc_ for details.
|
|
54
55
|
:usecrlf => false, # Use CRLF command and header line ends (1.2+)
|
55
56
|
:max_hbread_fails => 0, # Max HB read fails before retry. 0 => never retry
|
56
57
|
:max_hbrlck_fails => 0, # Max HB read lock obtain fails before retry. 0 => never retry
|
58
|
+
:fast_hbs_adjust => 0.0, # Fast heartbeat senders sleep adjustment, seconds, needed ...
|
59
|
+
# For fast heartbeat senders. 'fast' == YMMV. If not
|
60
|
+
# correct for your environment, expect unnecessary fail overs
|
57
61
|
}
|
58
62
|
|
59
63
|
# for client
|
data/examples/slogger.rb
CHANGED
@@ -203,7 +203,7 @@ class Slogger
|
|
203
203
|
end
|
204
204
|
|
205
205
|
# Stomp 1.1+ - heart beat read (receive) failed.
|
206
|
-
def on_hbread_fail(parms, ticker_data)
|
206
|
+
def on_hbread_fail(parms, ticker_data = {})
|
207
207
|
begin
|
208
208
|
@log.debug "Hbreadf Parms #{info(parms)}"
|
209
209
|
@log.debug "Hbreadf Result #{ticker_data.inspect}"
|
@@ -213,7 +213,7 @@ class Slogger
|
|
213
213
|
end
|
214
214
|
|
215
215
|
# Stomp 1.1+ - heart beat send (transmit) failed.
|
216
|
-
def on_hbwrite_fail(parms, ticker_data)
|
216
|
+
def on_hbwrite_fail(parms, ticker_data = {})
|
217
217
|
begin
|
218
218
|
@log.debug "Hbwritef Parms #{info(parms)}"
|
219
219
|
@log.debug "Hbwritef Result #{ticker_data.inspect}"
|
@@ -256,7 +256,7 @@ class Slogger
|
|
256
256
|
end
|
257
257
|
|
258
258
|
# Log heart beat fires
|
259
|
-
def on_hbfire(parms, srind,
|
259
|
+
def on_hbfire(parms, srind, firedata = {})
|
260
260
|
begin
|
261
261
|
@log.debug "HeartBeat Fire Parms #{info(parms)}"
|
262
262
|
@log.debug "HeartBeat Fire Send/Receive #{srind}"
|
data/lib/client/utils.rb
CHANGED
@@ -21,43 +21,43 @@ module Stomp
|
|
21
21
|
@reliable = true
|
22
22
|
true
|
23
23
|
end
|
24
|
-
private :parse_hash_params
|
25
24
|
|
26
25
|
def parse_stomp_url(login)
|
27
|
-
regexp = /^stomp:\/\/#{
|
26
|
+
regexp = /^stomp:\/\/#{URL_REPAT}/
|
28
27
|
return false unless login =~ regexp
|
29
28
|
|
30
|
-
@login = $
|
31
|
-
@passcode = $
|
32
|
-
@host = $
|
33
|
-
@port = $
|
29
|
+
@login = $3 || ""
|
30
|
+
@passcode = $4 || ""
|
31
|
+
@host = $5
|
32
|
+
@port = $6.to_i
|
33
|
+
|
34
34
|
@reliable = false
|
35
35
|
true
|
36
36
|
end
|
37
|
-
private :parse_stomp_url
|
38
37
|
|
39
38
|
# e.g. failover://(stomp://login1:passcode1@localhost:61616,stomp://login2:passcode2@remotehost:61617)?option1=param
|
40
39
|
def parse_failover_url(login)
|
41
|
-
|
42
|
-
|
43
|
-
|
44
|
-
|
45
|
-
|
46
|
-
|
47
|
-
|
48
|
-
|
49
|
-
|
50
|
-
|
51
|
-
|
52
|
-
|
53
|
-
|
54
|
-
|
55
|
-
|
56
|
-
|
57
|
-
|
58
|
-
|
40
|
+
rval = nil
|
41
|
+
if md = FAILOVER_REGEX.match(login)
|
42
|
+
finhosts = parse_hosts(login)
|
43
|
+
#
|
44
|
+
@login = finhosts[0][:login] || ""
|
45
|
+
@passcode = finhosts[0][:passcode] || ""
|
46
|
+
@host = finhosts[0][:host] || ""
|
47
|
+
@port = finhosts[0][:port] || ""
|
48
|
+
#
|
49
|
+
options = {}
|
50
|
+
if md_last = md[md.size-1]
|
51
|
+
parts = md_last.split(/&|=/)
|
52
|
+
raise Stomp::Error::MalformedFailoverOptionsError unless (parts.size % 2 ) == 0
|
53
|
+
options = Hash[*parts]
|
54
|
+
end
|
55
|
+
@parameters = {:hosts => finhosts}.merge! filter_options(options)
|
56
|
+
@reliable = true
|
57
|
+
rval = true
|
58
|
+
end
|
59
|
+
rval
|
59
60
|
end
|
60
|
-
private :parse_failover_url
|
61
61
|
|
62
62
|
def parse_positional_params(login, passcode, host, port, reliable)
|
63
63
|
@login = login
|
@@ -67,7 +67,6 @@ module Stomp
|
|
67
67
|
@reliable = reliable
|
68
68
|
true
|
69
69
|
end
|
70
|
-
private :parse_positional_params
|
71
70
|
|
72
71
|
# Set a subscription id in the headers hash if one does not already exist.
|
73
72
|
# For simplicities sake, all subscriptions have a subscription ID.
|
@@ -91,29 +90,21 @@ module Stomp
|
|
91
90
|
id
|
92
91
|
end
|
93
92
|
|
94
|
-
|
95
|
-
|
96
|
-
|
97
|
-
|
98
|
-
|
99
|
-
|
100
|
-
|
101
|
-
|
102
|
-
|
103
|
-
|
104
|
-
|
105
|
-
|
106
|
-
|
107
|
-
|
108
|
-
|
109
|
-
host[:host] = match[4]
|
110
|
-
host[:port] = match[5].to_i
|
111
|
-
|
112
|
-
hosts << host
|
113
|
-
end
|
114
|
-
|
115
|
-
hosts
|
116
|
-
end
|
93
|
+
# Parse a stomp URL.
|
94
|
+
def parse_hosts(url)
|
95
|
+
hosts = []
|
96
|
+
host_match = /stomp(\+ssl)?:\/\/#{URL_REPAT}/
|
97
|
+
url.scan(host_match).each do |match|
|
98
|
+
host = {}
|
99
|
+
host[:ssl] = match[0] == "+ssl" ? true : false
|
100
|
+
host[:login] = match[3] || ""
|
101
|
+
host[:passcode] = match[4] || ""
|
102
|
+
host[:host] = match[5]
|
103
|
+
host[:port] = match[6].to_i
|
104
|
+
hosts << host
|
105
|
+
end
|
106
|
+
hosts
|
107
|
+
end
|
117
108
|
|
118
109
|
# A very basic check of required arguments.
|
119
110
|
def check_arguments!()
|
@@ -161,14 +152,16 @@ module Stomp
|
|
161
152
|
if message.nil? && (!@reliable)
|
162
153
|
raise Stomp::Error::NilMessageError
|
163
154
|
end
|
155
|
+
if message # message can be nil on rapid AMQ stop / start sequences
|
164
156
|
# OK, we have some real data
|
165
|
-
|
166
|
-
|
167
|
-
|
168
|
-
|
169
|
-
|
170
|
-
|
171
|
-
|
157
|
+
if message.command == Stomp::CMD_MESSAGE
|
158
|
+
if listener = find_listener(message)
|
159
|
+
listener.call(message)
|
160
|
+
end
|
161
|
+
elsif message.command == Stomp::CMD_RECEIPT
|
162
|
+
if listener = @receipt_listeners[message.headers['receipt-id']]
|
163
|
+
listener.call(message)
|
164
|
+
end
|
172
165
|
end
|
173
166
|
end
|
174
167
|
end # while true
|
@@ -91,18 +91,28 @@ module Stomp
|
|
91
91
|
def _start_send_ticker()
|
92
92
|
sleeptime = @hbsend_interval / 1000000.0 # Sleep time secs
|
93
93
|
reconn = false
|
94
|
+
adjust = 0.0
|
94
95
|
@st = Thread.new {
|
96
|
+
first_time = true
|
95
97
|
while true do
|
96
|
-
|
98
|
+
#
|
99
|
+
slt = sleeptime - adjust - @fast_hbs_adjust
|
100
|
+
sleep(slt)
|
97
101
|
next unless @socket # nil under some circumstances ??
|
98
102
|
curt = Time.now.to_f
|
99
103
|
if @logger && @logger.respond_to?(:on_hbfire)
|
100
|
-
@logger.on_hbfire(log_params, "send_fire", curt)
|
104
|
+
@logger.on_hbfire(log_params, "send_fire", :curt => curt, :last_sleep => slt)
|
101
105
|
end
|
102
106
|
delta = curt - @ls
|
103
|
-
|
107
|
+
# Be tolerant (minus), and always do this the first time through.
|
108
|
+
# Reintroduce logic removed in d922fa.
|
109
|
+
compval = (@hbsend_interval - (@hbsend_interval/5.0)) / 1000000.0
|
110
|
+
if delta > compval || first_time
|
111
|
+
first_time = false
|
104
112
|
if @logger && @logger.respond_to?(:on_hbfire)
|
105
|
-
@logger.on_hbfire(log_params, "send_heartbeat",
|
113
|
+
@logger.on_hbfire(log_params, "send_heartbeat", :last_sleep => slt,
|
114
|
+
:curt => curt, :last_send => @ls, :delta => delta,
|
115
|
+
:compval => compval)
|
106
116
|
end
|
107
117
|
# Send a heartbeat
|
108
118
|
@transmit_semaphore.synchronize do
|
@@ -135,6 +145,7 @@ module Stomp
|
|
135
145
|
Thread.exit # This sender thread is done
|
136
146
|
end
|
137
147
|
end
|
148
|
+
adjust = Time.now.to_f - curt
|
138
149
|
Thread.pass
|
139
150
|
end
|
140
151
|
}
|
@@ -155,17 +166,15 @@ module Stomp
|
|
155
166
|
rdrdy = _is_ready?(@socket)
|
156
167
|
curt = Time.now.to_f
|
157
168
|
if @logger && @logger.respond_to?(:on_hbfire)
|
158
|
-
@logger.on_hbfire(log_params, "receive_fire", curt)
|
169
|
+
@logger.on_hbfire(log_params, "receive_fire", :curt => curt)
|
159
170
|
end
|
160
|
-
|
161
171
|
#
|
162
172
|
begin
|
163
173
|
delta = curt - @lr
|
164
174
|
if delta > sleeptime
|
165
175
|
if @logger && @logger.respond_to?(:on_hbfire)
|
166
|
-
@logger.on_hbfire(log_params, "receive_heartbeat",
|
176
|
+
@logger.on_hbfire(log_params, "receive_heartbeat", {})
|
167
177
|
end
|
168
|
-
|
169
178
|
# Client code could be off doing something else (that is, no reading of
|
170
179
|
# the socket has been requested by the caller). Try to handle that case.
|
171
180
|
lock = @read_semaphore.try_lock
|
@@ -223,7 +232,6 @@ module Stomp
|
|
223
232
|
end
|
224
233
|
fail_hard = true
|
225
234
|
end
|
226
|
-
|
227
235
|
# Do we want to attempt a retry?
|
228
236
|
if @reliable
|
229
237
|
# Retry on hard fail or max read fails
|
@@ -245,7 +253,6 @@ module Stomp
|
|
245
253
|
Thread.exit # This receiver thread is done
|
246
254
|
end
|
247
255
|
end
|
248
|
-
|
249
256
|
Thread.pass # Prior to next receive loop
|
250
257
|
#
|
251
258
|
end # of the "while true"
|
data/lib/connection/netio.rb
CHANGED
@@ -279,7 +279,6 @@ module Stomp
|
|
279
279
|
if @ssl.ciphers # User ciphers list?
|
280
280
|
ctx.ciphers = @ssl.ciphers # Accept user supplied ciphers
|
281
281
|
else
|
282
|
-
ctx.ciphers = Stomp::DEFAULT_CIPHERS # Just use Stomp defaults
|
283
282
|
end
|
284
283
|
end
|
285
284
|
end
|
@@ -292,6 +291,7 @@ module Stomp
|
|
292
291
|
|
293
292
|
Timeout::timeout(@connect_timeout, Stomp::Error::SocketOpenTimeout) do
|
294
293
|
ssl = OpenSSL::SSL::SSLSocket.new(open_tcp_socket, ctx)
|
294
|
+
ssl.hostname = @host if ssl.respond_to? :hostname=
|
295
295
|
ssl.sync_close = true # Sync ssl close with underlying TCP socket
|
296
296
|
ssl.connect
|
297
297
|
end
|
data/lib/connection/utils.rb
CHANGED
@@ -181,6 +181,7 @@ module Stomp
|
|
181
181
|
:stompconn => false,
|
182
182
|
:max_hbread_fails => 0,
|
183
183
|
:max_hbrlck_fails => 0,
|
184
|
+
:fast_hbs_adjust => 0.0,
|
184
185
|
}
|
185
186
|
|
186
187
|
res_params = default_params.merge(params)
|
@@ -229,6 +230,8 @@ module Stomp
|
|
229
230
|
begin
|
230
231
|
used_socket = socket()
|
231
232
|
return _receive(used_socket)
|
233
|
+
rescue Stomp::Error::MaxReconnectAttempts
|
234
|
+
raise
|
232
235
|
rescue
|
233
236
|
@failure = $!
|
234
237
|
raise unless @reliable
|
data/lib/stomp/client.rb
CHANGED
data/lib/stomp/connection.rb
CHANGED
@@ -70,6 +70,7 @@ module Stomp
|
|
70
70
|
# :usecrlf => false,
|
71
71
|
# :max_hbread_fails => 0,
|
72
72
|
# :max_hbrlck_fails => 0,
|
73
|
+
# :fast_hbs_adjust => 0.0,
|
73
74
|
# }
|
74
75
|
#
|
75
76
|
# e.g. c = Stomp::Connection.new(hash)
|
@@ -116,6 +117,7 @@ module Stomp
|
|
116
117
|
@usecrlf = false # If true, use \r\n as line ends (1.2 only)
|
117
118
|
@max_hbread_fails = 0 # 0 means never retry for HB read failures
|
118
119
|
@max_hbrlck_fails = 0 # 0 means never retry for HB read lock failures
|
120
|
+
@fast_hbs_adjust = 0.0 # Fast heartbeat senders sleep adjustment
|
119
121
|
warn "login looks like a URL, do you have the correct parameters?" if @login =~ /:\/\//
|
120
122
|
end
|
121
123
|
|
@@ -150,6 +152,7 @@ module Stomp
|
|
150
152
|
@usecrlf = @parameters[:usecrlf]
|
151
153
|
@max_hbread_fails = @parameters[:max_hbread_fails]
|
152
154
|
@max_hbrlck_fails = @parameters[:max_hbrlck_fails]
|
155
|
+
@fast_hbs_adjust = @parameters[:fast_hbs_adjust]
|
153
156
|
#sets the first host to connect
|
154
157
|
change_host
|
155
158
|
end
|
@@ -397,7 +400,10 @@ module Stomp
|
|
397
400
|
receive()
|
398
401
|
end
|
399
402
|
|
400
|
-
# receive returns the next Message off of the wire.
|
403
|
+
# receive returns the next Message off of the wire. this can return nil
|
404
|
+
# in cases where:
|
405
|
+
# * the broker has closed the connection
|
406
|
+
# * the connection is not reliable
|
401
407
|
def receive()
|
402
408
|
raise Stomp::Error::NoCurrentConnection if @closed_check && closed?
|
403
409
|
super_result = __old_receive()
|
@@ -417,6 +423,13 @@ module Stomp
|
|
417
423
|
super_result = __old_receive()
|
418
424
|
end
|
419
425
|
#
|
426
|
+
if super_result.nil? && !@reliable
|
427
|
+
@st.kill if @st # Kill ticker thread if any
|
428
|
+
@rt.kill if @rt # Kill ticker thread if any
|
429
|
+
close_socket()
|
430
|
+
@closed = true
|
431
|
+
warn 'warning: broker sent EOF, and connection not reliable' unless defined?(Test)
|
432
|
+
end
|
420
433
|
if @logger && @logger.respond_to?(:on_receive)
|
421
434
|
@logger.on_receive(log_params, super_result)
|
422
435
|
end
|
data/lib/stomp/constants.rb
CHANGED
@@ -111,4 +111,11 @@ module Stomp
|
|
111
111
|
["EXP-RC4-MD5", "TLSv1/SSLv3", 40, 128],
|
112
112
|
]
|
113
113
|
|
114
|
+
# stomp URL regex pattern, for e.g. login:passcode@host:port or host:port
|
115
|
+
URL_REPAT = '((([\w~!@#$%^&*()\-+=.?:<>,.]*\w):([\w~!@#$%^&*()\-+=.?:<>,.]*))?@)?([\w\.\-]+):(\d+)'
|
116
|
+
|
117
|
+
# Failover URL regex, for e.g.
|
118
|
+
#failover:(stomp+ssl://login1:passcode1@remotehost1:61612,stomp://login2:passcode2@remotehost2:61613)
|
119
|
+
FAILOVER_REGEX = /^failover:(\/\/)?\(stomp(\+ssl)?:\/\/#{URL_REPAT}(,stomp(\+ssl)?:\/\/#{URL_REPAT})*\)(\?(.*))?$/
|
120
|
+
|
114
121
|
end # Module Stomp
|
data/lib/stomp/errors.rb
CHANGED
@@ -205,6 +205,14 @@ module Stomp
|
|
205
205
|
end
|
206
206
|
end
|
207
207
|
|
208
|
+
# MalformedFailoverOptionsError is raised if failover URL
|
209
|
+
# options can not be parsed
|
210
|
+
class MalformedFailoverOptionsError < RuntimeError
|
211
|
+
def message
|
212
|
+
"failover options are malformed"
|
213
|
+
end
|
214
|
+
end
|
215
|
+
|
208
216
|
end # module Error
|
209
217
|
|
210
218
|
end # module Stomp
|
data/lib/stomp/version.rb
CHANGED
data/notes/heartbeat_readme.txt
CHANGED
@@ -77,6 +77,18 @@ error).
|
|
77
77
|
|
78
78
|
-----------------------------------------------------------
|
79
79
|
|
80
|
+
General advice:
|
81
|
+
|
82
|
+
Set your heartbeat intervals to the maximum possible to obtain your desired
|
83
|
+
behavior. Do *not* set them at extremely low values even if the broker allows
|
84
|
+
that. An absurd example:
|
85
|
+
|
86
|
+
heart-beat:1,1
|
87
|
+
|
88
|
+
which will likely not work well.
|
89
|
+
|
90
|
+
-----------------------------------------------------------
|
91
|
+
|
80
92
|
General notes:
|
81
93
|
|
82
94
|
In your real world apps, think about whether one or both of these parameters
|
@@ -98,6 +110,60 @@ We have done a variety of informal tests here, using both server kill and
|
|
98
110
|
packet drop strategies as appropriate. We believe more real world testing is
|
99
111
|
required.
|
100
112
|
|
101
|
-
|
102
|
-
|
113
|
+
-----------------------------------------------------------
|
114
|
+
|
115
|
+
08/07/2013
|
116
|
+
|
117
|
+
Issue #63 related, specifically fast send heart beats are being used and
|
118
|
+
spurious fail overs occur in rapid succession.
|
119
|
+
|
120
|
+
Background:
|
121
|
+
|
122
|
+
Fail over from heartbeat failures was introduced in gem version 1.2.10.
|
123
|
+
|
124
|
+
Subsequently:
|
125
|
+
|
126
|
+
This issue has been observed and documented in the following environment:
|
127
|
+
|
128
|
+
-- JRuby engine 1.7.4 *and*
|
129
|
+
-- ActiveMQ 5.8.0 *and*
|
130
|
+
-- 'fast' client send heartbeats
|
131
|
+
|
132
|
+
Heartbeat sends were at 2000ms.
|
133
|
+
|
134
|
+
At this point in time, fast send heart beats and spurious fail overs have
|
135
|
+
*not* been observed using:
|
136
|
+
|
137
|
+
-- Any native RUBY_ENGINE and ActiveMQ
|
138
|
+
-- Any native RUBY_ENGINE and Apollo (client send rates are limited by default)
|
139
|
+
-- Any native RUBY_ENGINE and RabbitMQ
|
140
|
+
-- JRuby and Apollo (client send rates are limited by default)
|
141
|
+
-- JRuby and RabbitMQ
|
142
|
+
|
143
|
+
Note that 'fast' will depend on your use case for heartbeats. Observations
|
144
|
+
are that sending heartbeat times less than 5000ms might be considered 'fast'
|
145
|
+
in the targeted environment.
|
146
|
+
|
147
|
+
The solution / bypass being put in place as of the above date was developed
|
148
|
+
through experimentation and is as follows:
|
149
|
+
|
150
|
+
- Add 'adjustment' logic to the heartbeat sender (thanks to ppaul for this idea).
|
151
|
+
- Re-introduce tolerance logic removed in d922fa.
|
152
|
+
- Add a new connection hash parameter to adjust heartbeat sends.
|
153
|
+
|
154
|
+
The newly introduced connection hash parameter is:
|
155
|
+
|
156
|
+
:fast_hbs_adjust => 0.0 # The default, no adjustment to sender sleep times (sec)
|
157
|
+
|
158
|
+
Recommendation for gem users that:
|
159
|
+
|
160
|
+
- Use fast send heartbeats
|
161
|
+
- Actually notice spurious fail overs
|
162
|
+
|
163
|
+
is to provide a very sender sleep time adjustment when connecting. Examples:
|
164
|
+
|
165
|
+
:fast_hbs_adjust => 0.05 # 50 milliseconds
|
166
|
+
:fast_hbs_adjust => 0.10 # 100 milliseconds
|
167
|
+
|
168
|
+
As usual, YMMV.
|
103
169
|
|
data/spec/client_spec.rb
CHANGED
@@ -254,7 +254,7 @@ describe Stomp::Client do
|
|
254
254
|
end
|
255
255
|
|
256
256
|
it "should properly parse a URL with failover:" do
|
257
|
-
url = "failover:(stomp://login1:passcode1@localhost:61616,stomp://login2:passcode2@remotehost1:61617
|
257
|
+
url = "failover:(stomp://login1:passcode1@localhost:61616,stomp://login2:passcode2@remotehost1:61617,stomp://login3:passcode3@remotehost2:61618)"
|
258
258
|
|
259
259
|
@parameters[:hosts] = [
|
260
260
|
{:login => "login1", :passcode => "passcode1", :host => "localhost", :port => 61616, :ssl => false},
|
@@ -283,7 +283,7 @@ describe Stomp::Client do
|
|
283
283
|
end
|
284
284
|
|
285
285
|
it "should properly parse a URL with user and/or password blank" do
|
286
|
-
url = "failover:(stomp
|
286
|
+
url = "failover:(stomp://@localhost:61616,stomp://@remotehost:61617)"
|
287
287
|
|
288
288
|
@parameters[:hosts] = [
|
289
289
|
{:login => "", :passcode => "", :host => "localhost", :port => 61616, :ssl => false},
|
data/spec/connection_spec.rb
CHANGED
@@ -27,6 +27,7 @@ describe Stomp::Connection do
|
|
27
27
|
:usecrlf => false,
|
28
28
|
:max_hbread_fails => 0,
|
29
29
|
:max_hbrlck_fails => 0,
|
30
|
+
:fast_hbs_adjust => 0.0,
|
30
31
|
}
|
31
32
|
|
32
33
|
#POG:
|
@@ -89,11 +90,12 @@ describe Stomp::Connection do
|
|
89
90
|
"backOffMultiplier" => 2,
|
90
91
|
"maxReconnectAttempts" => 0,
|
91
92
|
"randomize" => false,
|
92
|
-
"
|
93
|
-
"
|
93
|
+
"connectTimeout" => 0,
|
94
|
+
"parseTimeout" => 5,
|
94
95
|
"usecrlf" => false,
|
95
|
-
:
|
96
|
-
:
|
96
|
+
:maxHbreadFails => 0,
|
97
|
+
:maxHbrlckFails => 0,
|
98
|
+
:fastHbsAdjust => 0.0,
|
97
99
|
}
|
98
100
|
|
99
101
|
@connection = Stomp::Connection.new(used_hash)
|
@@ -272,7 +274,9 @@ describe Stomp::Connection do
|
|
272
274
|
|
273
275
|
before(:each) do
|
274
276
|
ssl_parameters = {:hosts => [{:login => "login2", :passcode => "passcode2", :host => "remotehost", :ssl => true}]}
|
275
|
-
@ssl_socket = mock(:ssl_socket, :puts => nil, :write => nil,
|
277
|
+
@ssl_socket = mock(:ssl_socket, :puts => nil, :write => nil,
|
278
|
+
:setsockopt => nil, :flush => true)
|
279
|
+
@ssl_socket.stub!(:sync_close=)
|
276
280
|
|
277
281
|
TCPSocket.should_receive(:open).and_return @tcp_socket
|
278
282
|
OpenSSL::SSL::SSLSocket.should_receive(:new).and_return(@ssl_socket)
|
@@ -344,6 +348,7 @@ describe Stomp::Connection do
|
|
344
348
|
:stompconn => false,
|
345
349
|
:max_hbread_fails => 0,
|
346
350
|
:max_hbrlck_fails => 0,
|
351
|
+
:fast_hbs_adjust => 0.0,
|
347
352
|
}
|
348
353
|
|
349
354
|
used_hash = {
|
@@ -382,6 +387,7 @@ describe Stomp::Connection do
|
|
382
387
|
:usecrlf => true,
|
383
388
|
:max_hbread_fails => 123,
|
384
389
|
:max_hbrlck_fails => 456,
|
390
|
+
:fast_hbs_adjust => 0.2,
|
385
391
|
}
|
386
392
|
|
387
393
|
@connection = Stomp::Connection.new(used_hash)
|
@@ -430,7 +436,14 @@ describe Stomp::Connection do
|
|
430
436
|
|
431
437
|
@connection.instance_variable_set(:@connection_attempts, limit)
|
432
438
|
@connection.send(:max_reconnect_attempts?).should be_true
|
439
|
+
end
|
440
|
+
|
441
|
+
# These should be raised for the user to deal with
|
442
|
+
it "should not rescue MaxReconnectAttempts" do
|
443
|
+
@connection = Stomp::Connection.new(@parameters)
|
444
|
+
@connection.stub(:socket).and_raise(Stomp::Error::MaxReconnectAttempts)
|
433
445
|
|
446
|
+
expect { @connection.receive() }.to raise_error
|
434
447
|
end
|
435
448
|
end
|
436
449
|
|
data/stomp.gemspec
CHANGED
@@ -5,11 +5,11 @@
|
|
5
5
|
|
6
6
|
Gem::Specification.new do |s|
|
7
7
|
s.name = %q{stomp}
|
8
|
-
s.version = "1.2.
|
8
|
+
s.version = "1.2.12"
|
9
9
|
|
10
10
|
s.required_rubygems_version = Gem::Requirement.new(">= 0") if s.respond_to? :required_rubygems_version=
|
11
11
|
s.authors = ["Brian McCallister", "Marius Mathiesen", "Thiago Morello", "Guy M. Allard"]
|
12
|
-
s.date = %q{2013-
|
12
|
+
s.date = %q{2013-08-11}
|
13
13
|
s.description = %q{Ruby client for the Stomp messaging protocol. Note that this gem is no longer supported on rubyforge.}
|
14
14
|
s.email = ["brianm@apache.org", "marius@stones.com", "morellon@gmail.com", "allard.guy.m@gmail.com"]
|
15
15
|
s.executables = ["catstomp", "stompcat"]
|
@@ -65,6 +65,7 @@ Gem::Specification.new do |s|
|
|
65
65
|
"test/test_helper.rb",
|
66
66
|
"test/test_message.rb",
|
67
67
|
"test/test_ssl.rb",
|
68
|
+
"test/test_urlogin.rb",
|
68
69
|
"test/tlogger.rb"
|
69
70
|
]
|
70
71
|
s.files = [
|
@@ -129,6 +130,7 @@ Gem::Specification.new do |s|
|
|
129
130
|
"test/test_helper.rb",
|
130
131
|
"test/test_message.rb",
|
131
132
|
"test/test_ssl.rb",
|
133
|
+
"test/test_urlogin.rb",
|
132
134
|
"test/tlogger.rb"
|
133
135
|
]
|
134
136
|
s.homepage = %q{https://github.com/stompgem/stomp}
|
data/test/test_connection.rb
CHANGED
@@ -484,10 +484,11 @@ class TestConnection < Test::Unit::TestCase
|
|
484
484
|
def test_conn10_simple
|
485
485
|
@conn.disconnect
|
486
486
|
#
|
487
|
+
vhost = ENV['STOMP_RABBIT'] ? "/" : host
|
487
488
|
hash = { :hosts => [
|
488
489
|
{:login => user, :passcode => passcode, :host => host, :port => port, :ssl => false},
|
489
490
|
],
|
490
|
-
:connect_headers => {"accept-version" => "1.0", "host" =>
|
491
|
+
:connect_headers => {"accept-version" => "1.0", "host" => vhost},
|
491
492
|
:reliable => false,
|
492
493
|
}
|
493
494
|
c = nil
|
@@ -499,7 +500,7 @@ class TestConnection < Test::Unit::TestCase
|
|
499
500
|
hash = { :hosts => [
|
500
501
|
{:login => user, :passcode => passcode, :host => host, :port => port, :ssl => false},
|
501
502
|
],
|
502
|
-
:connect_headers => {"accept-version" => "3.14159,1.0,12.0", "host" =>
|
503
|
+
:connect_headers => {"accept-version" => "3.14159,1.0,12.0", "host" => vhost},
|
503
504
|
:reliable => false,
|
504
505
|
}
|
505
506
|
c = nil
|
data/test/test_helper.rb
CHANGED
@@ -84,7 +84,7 @@ module TestBase
|
|
84
84
|
# Get a Stomp SSL Connection.
|
85
85
|
def get_ssl_connection()
|
86
86
|
ch = get_conn_headers()
|
87
|
-
ssl_params = Stomp::SSLParams.new
|
87
|
+
ssl_params = Stomp::SSLParams.new(:use_ruby_ciphers => jruby?())
|
88
88
|
hash = { :hosts => [
|
89
89
|
{:login => user, :passcode => passcode, :host => host, :port => ssl_port, :ssl => ssl_params},
|
90
90
|
],
|
@@ -164,5 +164,10 @@ module TestBase
|
|
164
164
|
end
|
165
165
|
end
|
166
166
|
|
167
|
+
# Check for JRuby before a connection exists
|
168
|
+
def jruby?()
|
169
|
+
jr = defined?(RUBY_ENGINE) && RUBY_ENGINE =~ /jruby/ ? true : false
|
170
|
+
end
|
171
|
+
|
167
172
|
end
|
168
173
|
|
@@ -0,0 +1,86 @@
|
|
1
|
+
# -*- encoding: utf-8 -*-
|
2
|
+
|
3
|
+
if Kernel.respond_to?(:require_relative)
|
4
|
+
require_relative("test_helper")
|
5
|
+
else
|
6
|
+
$:.unshift(File.dirname(__FILE__))
|
7
|
+
require 'test_helper'
|
8
|
+
end
|
9
|
+
|
10
|
+
=begin
|
11
|
+
|
12
|
+
Main class for testing Stomp::Client URL based Logins.
|
13
|
+
|
14
|
+
=end
|
15
|
+
class TestURLLogins < Test::Unit::TestCase
|
16
|
+
include TestBase
|
17
|
+
|
18
|
+
def setup
|
19
|
+
hostname = host()
|
20
|
+
portnum = port()
|
21
|
+
sslpn = ssl_port()
|
22
|
+
@tdstomp = [
|
23
|
+
"stomp://guestl:guestp@#{hostname}:#{portnum}",
|
24
|
+
"stomp://#{hostname}:#{portnum}",
|
25
|
+
"stomp://@#{hostname}:#{portnum}",
|
26
|
+
"stomp://f@#$$%^&*()_+=o.o:@#{hostname}:#{portnum}",
|
27
|
+
'stomp://f@#$$%^&*()_+=o.o::b~!@#$%^&*()+-_=?:<>,.@@' + hostname + ":#{portnum}",
|
28
|
+
]
|
29
|
+
@tdfailover = [
|
30
|
+
"failover://(stomp://#{hostname}:#{portnum})",
|
31
|
+
"failover://(stomp+ssl://#{hostname}:#{sslpn})",
|
32
|
+
"failover://(stomp://#{hostname}:#{portnum})",
|
33
|
+
"failover://(stomp://#{hostname}:#{portnum})?whatup=doc&coyote=kaboom",
|
34
|
+
"failover://(stomp://#{hostname}:#{portnum})?whatup=doc",
|
35
|
+
"failover://(stomp://#{hostname}:#{portnum})?whatup=doc&coyote=kaboom&randomize=true",
|
36
|
+
'failover://(stomp://f@#$$%^&*()_+=o.o::b~!@#$%^&*()+-_=?:<>,.@@' + "localhost" + ":#{portnum}" + ")",
|
37
|
+
'failover://(stomp://f@#$$%^&*()_+=o.o::b~!@#$%^&*()+-_=:<>,.@@' + "localhost" + ":#{portnum}" + ")",
|
38
|
+
'failover://(stomp://f@#$$%^&*()_+=o.o::b~!@#$%^&*()+-_=?:<>,.@@' + "localhost" + ":#{portnum}" + ")?a=b",
|
39
|
+
'failover://(stomp://f@#$$%^&*()_+=o.o::b~!@#$%^&*()+-_=:<>,.@@' + "localhost" + ":#{portnum}" + ")?c=d&e=f",
|
40
|
+
"failover://(stomp://usera:passa@#{hostname}:#{portnum})",
|
41
|
+
"failover://(stomp+ssl://usera:passa@#{hostname}:#{sslpn})",
|
42
|
+
"failover://(stomp://usera:@#{hostname}:#{portnum})",
|
43
|
+
"failover://(stomp://#{hostname}:#{portnum},stomp://#{hostname}:#{portnum})",
|
44
|
+
"failover://(stomp://usera:passa@#{hostname}:#{portnum},stomp://#{hostname}:#{portnum})",
|
45
|
+
"failover://(stomp://usera:@#{hostname}:#{portnum},stomp://#{hostname}:#{portnum})",
|
46
|
+
"failover://(stomp://usera:@#{hostname}:#{portnum},stomp+ssl://#{hostname}:#{sslpn})",
|
47
|
+
"failover://(stomp://#{hostname}:#{portnum},stomp://#{hostname}:#{portnum})?a=b&c=d",
|
48
|
+
"failover://(stomp://#{hostname}:#{portnum},stomp://#{hostname}:#{portnum})?a=b&c=d&connect_timeout=2020",
|
49
|
+
]
|
50
|
+
|
51
|
+
@badparms = "failover://(stomp://#{hostname}:#{portnum})?a=b&noequal"
|
52
|
+
end
|
53
|
+
|
54
|
+
def teardown
|
55
|
+
@client.close if @client && @client.open? # allow tests to close
|
56
|
+
end
|
57
|
+
|
58
|
+
# test stomp:// URLs
|
59
|
+
def test_0010_stomp_urls()
|
60
|
+
@tdstomp.each_with_index do |url, ndx|
|
61
|
+
c = Stomp::Client.new(url)
|
62
|
+
assert !c.nil?, url
|
63
|
+
assert c.open?, url
|
64
|
+
c.close
|
65
|
+
end
|
66
|
+
end
|
67
|
+
|
68
|
+
# test failover:// urls
|
69
|
+
def test_0020_failover_urls()
|
70
|
+
@tdfailover.each_with_index do |url, ndx|
|
71
|
+
c = Stomp::Client.new(url)
|
72
|
+
assert !c.nil?, url
|
73
|
+
assert c.open?, url
|
74
|
+
c.close
|
75
|
+
end
|
76
|
+
end
|
77
|
+
|
78
|
+
# test failover:// with bad parameters
|
79
|
+
def test_0020_failover_badparms()
|
80
|
+
assert_raise(Stomp::Error::MalformedFailoverOptionsError) {
|
81
|
+
c = Stomp::Client.new(@badparms)
|
82
|
+
}
|
83
|
+
end
|
84
|
+
|
85
|
+
end unless ENV['STOMP_RABBIT']
|
86
|
+
|
data/test/tlogger.rb
CHANGED
@@ -51,11 +51,11 @@ class Tlogger
|
|
51
51
|
end
|
52
52
|
|
53
53
|
# Stomp 1.1+ - heart beat thread fires
|
54
|
-
def on_hbfire(parms, type,
|
54
|
+
def on_hbfire(parms, type, firedata)
|
55
55
|
begin
|
56
56
|
@log.debug "HBfire #{type} " + "=" * 30
|
57
57
|
@log.debug "HBfire #{type} Parms #{info(parms)}"
|
58
|
-
@log.debug "HBfire #{type}
|
58
|
+
@log.debug "HBfire #{type} Firedata #{firedata.inspect}"
|
59
59
|
rescue
|
60
60
|
@log.debug "HBfire #{type} oops"
|
61
61
|
end
|
metadata
CHANGED
@@ -1,13 +1,13 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: stomp
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
hash:
|
4
|
+
hash: 7
|
5
5
|
prerelease: false
|
6
6
|
segments:
|
7
7
|
- 1
|
8
8
|
- 2
|
9
|
-
-
|
10
|
-
version: 1.2.
|
9
|
+
- 12
|
10
|
+
version: 1.2.12
|
11
11
|
platform: ruby
|
12
12
|
authors:
|
13
13
|
- Brian McCallister
|
@@ -18,7 +18,7 @@ autorequire:
|
|
18
18
|
bindir: bin
|
19
19
|
cert_chain: []
|
20
20
|
|
21
|
-
date: 2013-
|
21
|
+
date: 2013-08-11 00:00:00 -04:00
|
22
22
|
default_executable:
|
23
23
|
dependencies:
|
24
24
|
- !ruby/object:Gem::Dependency
|
@@ -99,6 +99,7 @@ extra_rdoc_files:
|
|
99
99
|
- test/test_helper.rb
|
100
100
|
- test/test_message.rb
|
101
101
|
- test/test_ssl.rb
|
102
|
+
- test/test_urlogin.rb
|
102
103
|
- test/tlogger.rb
|
103
104
|
files:
|
104
105
|
- CHANGELOG.rdoc
|
@@ -162,6 +163,7 @@ files:
|
|
162
163
|
- test/test_helper.rb
|
163
164
|
- test/test_message.rb
|
164
165
|
- test/test_ssl.rb
|
166
|
+
- test/test_urlogin.rb
|
165
167
|
- test/tlogger.rb
|
166
168
|
has_rdoc: true
|
167
169
|
homepage: https://github.com/stompgem/stomp
|