beetle 3.1.0 → 3.2.0
Sign up to get free protection for your applications and to get access to all the features.
- checksums.yaml +4 -4
- data/RELEASE_NOTES.rdoc +3 -0
- data/examples/attempts.rb +2 -2
- data/lib/beetle/handler.rb +1 -1
- data/lib/beetle/message.rb +12 -2
- data/lib/beetle/r_c.rb +1 -0
- data/lib/beetle/subscriber.rb +3 -3
- data/lib/beetle/version.rb +1 -1
- data/test/beetle/message_test.rb +39 -24
- metadata +2 -2
checksums.yaml
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
---
|
2
2
|
SHA256:
|
3
|
-
metadata.gz:
|
4
|
-
data.tar.gz:
|
3
|
+
metadata.gz: cfe005056abcea7bb999f5c1ffbc3300882e6625633034e0cc4ad7e8fc2b4d18
|
4
|
+
data.tar.gz: bc6a039a77d190c10878045420ce6fe57bb34d05cd343d71bbc8e9dc6832b74c
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: 284dc26f2ccdcf11df046f977e083ac35ff0f35d759da350508cdaffecdcf3b56579a06381818f613711b9b5b2c57ff7d044d106562b39530b983e4a4148268e
|
7
|
+
data.tar.gz: 962ba73a9f2580748e53e846a36fefcbc1ee9a1054a88a8f60f3de77b3824ac547deaa2c69e94995155400e1aca1ce39cd06779efd6d8910420a99d7b682ec07
|
data/RELEASE_NOTES.rdoc
CHANGED
data/examples/attempts.rb
CHANGED
@@ -15,8 +15,8 @@ Beetle.config.logger.level = Logger::INFO
|
|
15
15
|
|
16
16
|
# setup client
|
17
17
|
$client = Beetle::Client.new
|
18
|
-
$client.config.dead_lettering_enabled =
|
19
|
-
$client.config.lazy_queues_enabled =
|
18
|
+
$client.config.dead_lettering_enabled = false
|
19
|
+
$client.config.lazy_queues_enabled = false
|
20
20
|
$client.configure(:key => "my.test.message") do
|
21
21
|
message(:test)
|
22
22
|
queue(:test)
|
data/lib/beetle/handler.rb
CHANGED
data/lib/beetle/message.rb
CHANGED
@@ -257,11 +257,18 @@ module Beetle
|
|
257
257
|
|
258
258
|
# process this message and do not allow any exception to escape to the caller
|
259
259
|
def process(handler)
|
260
|
-
logger.debug "Beetle: processing message #{msg_id}(#{timestamp})"
|
261
260
|
result = nil
|
261
|
+
begin
|
262
|
+
# pre_process might set up log routing and it might raise
|
263
|
+
handler.pre_process(self)
|
264
|
+
rescue Exception => @pre_exception
|
265
|
+
Beetle::reraise_expectation_errors!
|
266
|
+
logger.error "Beetle: preprocessing error #{@pre_exception.class}(#{@pre_exception}) for #{msg_id}"
|
267
|
+
end
|
268
|
+
logger.debug "Beetle: processing message #{msg_id}(#{timestamp})"
|
262
269
|
begin
|
263
270
|
result = process_internal(handler)
|
264
|
-
handler.process_exception(@exception) if @exception
|
271
|
+
handler.process_exception(@exception || @pre_exception) if (@exception || @pre_exception)
|
265
272
|
handler.process_failure(result) if result.failure?
|
266
273
|
rescue Exception => e
|
267
274
|
Beetle::reraise_expectation_errors!
|
@@ -278,6 +285,9 @@ module Beetle
|
|
278
285
|
if @exception
|
279
286
|
ack!
|
280
287
|
RC::DecodingError
|
288
|
+
elsif @pre_exception
|
289
|
+
ack!
|
290
|
+
RC::PreprocessingError
|
281
291
|
elsif expired?
|
282
292
|
logger.warn "Beetle: ignored expired message (#{msg_id})!"
|
283
293
|
ack!
|
data/lib/beetle/r_c.rb
CHANGED
data/lib/beetle/subscriber.rb
CHANGED
@@ -175,10 +175,9 @@ module Beetle
|
|
175
175
|
return
|
176
176
|
end
|
177
177
|
begin
|
178
|
-
processor = Handler.create(handler, opts)
|
179
|
-
processor.pre_process
|
180
178
|
message_options = opts.merge(:server => server, :store => @client.deduplication_store)
|
181
179
|
m = Message.new(amqp_queue_name, header, data, message_options)
|
180
|
+
processor = Handler.create(handler, opts)
|
182
181
|
result = m.process(processor)
|
183
182
|
if result.reject?
|
184
183
|
if @client.config.dead_lettering_enabled?
|
@@ -203,7 +202,8 @@ module Beetle
|
|
203
202
|
logger.debug "Beetle: completed #{msg_id}"
|
204
203
|
begin
|
205
204
|
processor.post_process
|
206
|
-
rescue Exception
|
205
|
+
rescue Exception => e
|
206
|
+
logger.error "Beetle: post_process error #{e.class}(#{e}) for #{msg_id}"
|
207
207
|
Beetle::reraise_expectation_errors!
|
208
208
|
end
|
209
209
|
end
|
data/lib/beetle/version.rb
CHANGED
data/test/beetle/message_test.rb
CHANGED
@@ -117,6 +117,7 @@ module Beetle
|
|
117
117
|
def setup
|
118
118
|
@store = DeduplicationStore.new
|
119
119
|
@store.flushdb
|
120
|
+
@null_handler = Handler.create(lambda {|*args|})
|
120
121
|
end
|
121
122
|
|
122
123
|
test "should be able to extract msg_id from any key" do
|
@@ -135,7 +136,7 @@ module Beetle
|
|
135
136
|
assert !message.expired?
|
136
137
|
assert !message.redundant?
|
137
138
|
|
138
|
-
message.process(
|
139
|
+
message.process(@null_handler)
|
139
140
|
|
140
141
|
@store.keys(message.msg_id).each do |key|
|
141
142
|
assert !@store.redis.exists(key)
|
@@ -150,8 +151,8 @@ module Beetle
|
|
150
151
|
assert !message.expired?
|
151
152
|
assert message.redundant?
|
152
153
|
|
153
|
-
message.process(
|
154
|
-
message.process(
|
154
|
+
message.process(@null_handler)
|
155
|
+
message.process(@null_handler)
|
155
156
|
|
156
157
|
@store.keys(message.msg_id).each do |key|
|
157
158
|
assert !@store.redis.exists(key)
|
@@ -166,7 +167,7 @@ module Beetle
|
|
166
167
|
assert !message.expired?
|
167
168
|
assert message.redundant?
|
168
169
|
|
169
|
-
message.process(
|
170
|
+
message.process(@null_handler)
|
170
171
|
|
171
172
|
assert @store.exists(message.msg_id, :status)
|
172
173
|
assert @store.exists(message.msg_id, :expires)
|
@@ -183,6 +184,7 @@ module Beetle
|
|
183
184
|
def setup
|
184
185
|
@store = DeduplicationStore.new
|
185
186
|
@store.flushdb
|
187
|
+
@null_handler = Handler.create(lambda {|*args|})
|
186
188
|
end
|
187
189
|
|
188
190
|
test "an expired message should be acked without calling the handler" do
|
@@ -192,7 +194,7 @@ module Beetle
|
|
192
194
|
assert message.expired?
|
193
195
|
|
194
196
|
processed = :no
|
195
|
-
message.process(lambda {|*args| processed = true})
|
197
|
+
message.process(Handler.create(lambda {|*args| processed = true}))
|
196
198
|
assert_equal :no, processed
|
197
199
|
end
|
198
200
|
|
@@ -205,7 +207,7 @@ module Beetle
|
|
205
207
|
assert message.delayed?
|
206
208
|
|
207
209
|
processed = :no
|
208
|
-
message.process(lambda {|*args| processed = true})
|
210
|
+
message.process(Handler.create(lambda {|*args| processed = true}))
|
209
211
|
assert_equal :no, processed
|
210
212
|
end
|
211
213
|
|
@@ -214,7 +216,7 @@ module Beetle
|
|
214
216
|
header.expects(:ack)
|
215
217
|
message = Message.new("somequeue", header, 'foo', :store => @store)
|
216
218
|
|
217
|
-
message.process(
|
219
|
+
message.process(@null_handler)
|
218
220
|
assert !message.redundant?
|
219
221
|
assert !@store.exists(message.msg_id, :ack_count)
|
220
222
|
end
|
@@ -225,7 +227,7 @@ module Beetle
|
|
225
227
|
|
226
228
|
message.expects(:ack!)
|
227
229
|
assert message.redundant?
|
228
|
-
message.process(
|
230
|
+
message.process(@null_handler)
|
229
231
|
end
|
230
232
|
|
231
233
|
test "acking a redundant message should increment the ack_count key" do
|
@@ -234,7 +236,7 @@ module Beetle
|
|
234
236
|
message = Message.new("somequeue", header, 'foo', :store => @store)
|
235
237
|
|
236
238
|
assert_nil @store.get(message.msg_id, :ack_count)
|
237
|
-
message.process(
|
239
|
+
message.process(@null_handler)
|
238
240
|
assert message.redundant?
|
239
241
|
assert_equal "1", @store.get(message.msg_id, :ack_count)
|
240
242
|
end
|
@@ -244,8 +246,8 @@ module Beetle
|
|
244
246
|
header.expects(:ack).twice
|
245
247
|
message = Message.new("somequeue", header, 'foo', :store => @store)
|
246
248
|
|
247
|
-
message.process(
|
248
|
-
message.process(
|
249
|
+
message.process(@null_handler)
|
250
|
+
message.process(@null_handler)
|
249
251
|
assert message.redundant?
|
250
252
|
assert !@store.exists(message.msg_id, :ack_count)
|
251
253
|
end
|
@@ -263,11 +265,12 @@ module Beetle
|
|
263
265
|
message = Message.new("somequeue", header, 'foo', :attempts => 2, :store => @store)
|
264
266
|
assert !message.attempts_limit_reached?
|
265
267
|
|
266
|
-
|
268
|
+
handler = mock("handler")
|
267
269
|
s = sequence("s")
|
268
|
-
|
270
|
+
handler.expects(:pre_process).with(message).in_sequence(s)
|
271
|
+
handler.expects(:call).in_sequence(s)
|
269
272
|
header.expects(:ack).in_sequence(s)
|
270
|
-
assert_equal RC::OK, message.process(
|
273
|
+
assert_equal RC::OK, message.process(handler)
|
271
274
|
end
|
272
275
|
|
273
276
|
test "after processing a redundant fresh message successfully the ack count should be 1 and the status should be completed" do
|
@@ -298,25 +301,27 @@ module Beetle
|
|
298
301
|
header = header_with_params({})
|
299
302
|
message = Message.new("somequeue", header, 'foo', :attempts => 1, :store => @store)
|
300
303
|
|
301
|
-
|
304
|
+
handler = mock("handler")
|
302
305
|
s = sequence("s")
|
306
|
+
handler.expects(:pre_process).with(message).in_sequence(s)
|
303
307
|
header.expects(:ack).in_sequence(s)
|
304
|
-
|
305
|
-
assert_equal RC::OK, message.process(
|
308
|
+
handler.expects(:call).in_sequence(s)
|
309
|
+
assert_equal RC::OK, message.process(handler)
|
306
310
|
end
|
307
311
|
|
308
312
|
test "when processing a simple message, RC::AttemptsLimitReached should be returned if the handler crashes" do
|
309
313
|
header = header_with_params({})
|
310
314
|
message = Message.new("somequeue", header, 'foo', :attempts => 1, :store => @store)
|
311
315
|
|
312
|
-
|
316
|
+
handler = mock("handler")
|
313
317
|
s = sequence("s")
|
318
|
+
handler.expects(:pre_process).with(message).in_sequence(s)
|
314
319
|
header.expects(:ack).in_sequence(s)
|
315
320
|
e = Exception.new("ohoh")
|
316
|
-
|
317
|
-
|
318
|
-
|
319
|
-
assert_equal RC::AttemptsLimitReached, message.process(
|
321
|
+
handler.expects(:call).in_sequence(s).raises(e)
|
322
|
+
handler.expects(:process_exception).with(e).in_sequence(s)
|
323
|
+
handler.expects(:process_failure).with(RC::AttemptsLimitReached).in_sequence(s)
|
324
|
+
assert_equal RC::AttemptsLimitReached, message.process(handler)
|
320
325
|
end
|
321
326
|
|
322
327
|
end
|
@@ -422,7 +427,6 @@ module Beetle
|
|
422
427
|
assert !message.timed_out?
|
423
428
|
|
424
429
|
proc = lambda {|*args| raise "crash"}
|
425
|
-
s = sequence("s")
|
426
430
|
message.expects(:completed!).once
|
427
431
|
header.expects(:ack)
|
428
432
|
assert_equal RC::AttemptsLimitReached, message.__send__(:process_internal, proc)
|
@@ -436,7 +440,7 @@ module Beetle
|
|
436
440
|
@store.flushdb
|
437
441
|
end
|
438
442
|
|
439
|
-
test "a message with
|
443
|
+
test "a message with a decoding error should not be processed at all, but it should be acked" do
|
440
444
|
header = {}
|
441
445
|
message = Message.new("somequeue", header, 'foo')
|
442
446
|
assert message.exception
|
@@ -447,6 +451,17 @@ module Beetle
|
|
447
451
|
assert_equal RC::DecodingError, message.__send__(:process_internal, proc)
|
448
452
|
end
|
449
453
|
|
454
|
+
test "a message with a preprocessing error set should not be processed at all, but it should be acked" do
|
455
|
+
header = header_with_params({})
|
456
|
+
message = Message.new("somequeue", header, 'foo')
|
457
|
+
message.instance_eval { @pre_exception = StandardError.new("shoo") }
|
458
|
+
|
459
|
+
proc = mock("proc")
|
460
|
+
proc.expects(:call).never
|
461
|
+
message.expects(:ack!)
|
462
|
+
assert_equal RC::PreprocessingError, message.__send__(:process_internal, proc)
|
463
|
+
end
|
464
|
+
|
450
465
|
test "a completed existing message should be just acked and not run the handler" do
|
451
466
|
header = header_with_params({})
|
452
467
|
message = Message.new("somequeue", header, 'foo', :attempts => 2, :store => @store)
|
metadata
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: beetle
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 3.
|
4
|
+
version: 3.2.0
|
5
5
|
platform: ruby
|
6
6
|
authors:
|
7
7
|
- Stefan Kaes
|
@@ -12,7 +12,7 @@ authors:
|
|
12
12
|
autorequire:
|
13
13
|
bindir: bin
|
14
14
|
cert_chain: []
|
15
|
-
date: 2019-07-
|
15
|
+
date: 2019-07-09 00:00:00.000000000 Z
|
16
16
|
dependencies:
|
17
17
|
- !ruby/object:Gem::Dependency
|
18
18
|
name: bunny
|