stapfen 1.5.0 → 2.0.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- data/CHANGES.md +8 -0
- data/README.md +58 -25
- data/lib/stapfen/client/jms.rb +91 -0
- data/lib/stapfen/client/stomp.rb +35 -0
- data/lib/stapfen/client.rb +8 -0
- data/lib/stapfen/destination.rb +20 -0
- data/lib/stapfen/logger.rb +2 -2
- data/lib/stapfen/message.rb +0 -12
- data/lib/stapfen/version.rb +1 -1
- data/lib/stapfen/worker.rb +29 -66
- data/lib/stapfen.rb +15 -0
- data/spec/client/jms_spec.rb +106 -0
- data/spec/client/stomp_spec.rb +5 -0
- data/spec/client_spec.rb +5 -0
- data/spec/destination_spec.rb +13 -0
- data/spec/logger_spec.rb +1 -1
- data/spec/worker_spec.rb +35 -6
- metadata +14 -4
data/CHANGES.md
ADDED
@@ -0,0 +1,8 @@
|
|
1
|
+
# Changes to Stapfen
|
2
|
+
|
3
|
+
|
4
|
+
## 2.0.0
|
5
|
+
|
6
|
+
* Add support for JMS-backed `Stapfen::Worker` classes
|
7
|
+
* Deep copy the configuration passed into `Stomp::Client` to work-around [stomp #80](https://github.com/stompgem/stomp/issues/80)
|
8
|
+
* Support per-instance log configuration [#3](https://github.com/lookout/stapfen/issues/3)
|
data/README.md
CHANGED
@@ -1,6 +1,12 @@
|
|
1
1
|
# Stapfen
|
2
2
|
|
3
|
-
|
3
|
+
|
4
|
+
Stapfen is a simple gem to make writing workers that consume messages via
|
5
|
+
[STOMP](http://stomp.github.io/) or
|
6
|
+
[JMS](https://en.wikipedia.org/wiki/Java_Message_Service) easier.
|
7
|
+
|
8
|
+
Stapfen allows you to write one worker class, and use either protocol
|
9
|
+
depending on the environment and needs.
|
4
10
|
|
5
11
|
|
6
12
|
## Usage
|
@@ -10,37 +16,63 @@ Stapfen is a simple gem to make writing stand-alone STOMP workers easier.
|
|
10
16
|
|
11
17
|
Consider the following `myworker.rb` file:
|
12
18
|
|
13
|
-
|
14
|
-
|
15
|
-
|
16
|
-
|
17
|
-
|
18
|
-
|
19
|
-
|
20
|
-
|
21
|
-
|
22
|
-
|
23
|
-
|
24
|
-
|
25
|
-
|
26
|
-
|
27
|
-
|
28
|
-
|
29
|
-
|
30
|
-
|
31
|
-
|
32
|
-
|
33
|
-
|
34
|
-
|
35
|
-
|
36
|
-
|
19
|
+
```ruby
|
20
|
+
class MyWorker < Stapfen::Worker
|
21
|
+
use_stomp!
|
22
|
+
|
23
|
+
configure do
|
24
|
+
{
|
25
|
+
:hosts => [
|
26
|
+
{
|
27
|
+
:host => 'localhost',
|
28
|
+
:port => 61613,
|
29
|
+
:login => 'guest',
|
30
|
+
:passcode => 'guest',
|
31
|
+
:ssl => false
|
32
|
+
}
|
33
|
+
]
|
34
|
+
}
|
35
|
+
end
|
36
|
+
|
37
|
+
# [Optional] Set up a logger for each worker instance
|
38
|
+
log do
|
39
|
+
Logger.new(STDOUT)
|
40
|
+
end
|
41
|
+
|
42
|
+
consume 'thequeue', :dead_letter_queue => '/queue/dlq',
|
43
|
+
:max_redeliveries => 0 do |message|
|
44
|
+
|
45
|
+
data = expensive_computation(message.body)
|
46
|
+
# Save my data, or do something worker-specific with it
|
47
|
+
persist(data)
|
48
|
+
|
49
|
+
# Send another message
|
50
|
+
client.publish('/topic/computation-acks', "finished with #{message.message_id}")
|
51
|
+
end
|
52
|
+
|
53
|
+
end
|
54
|
+
|
55
|
+
MyWorker.run!
|
56
|
+
```
|
57
|
+
|
58
|
+
|
59
|
+
When using the STOMP protocol, the value returned from the `configure` block is expected to be a valid
|
37
60
|
`Stomp::Client` [connection
|
38
61
|
hash](https://github.com/stompgem/stomp#hash-login-example-usage-this-is-the-recommended-login-technique).
|
39
62
|
|
63
|
+
In the case of the JMS protocol, the value returned from the `configure` block
|
64
|
+
is expected to be a valid [configuration
|
65
|
+
hash](https://github.com/reidmorrison/jruby-jms#consumer) for the
|
66
|
+
[jruby-jms](https://github.com/reidmorrison/jruby-jms) gem.
|
67
|
+
|
68
|
+
---
|
69
|
+
|
40
70
|
It is also important to note that the `consume` block will be invoked inside an
|
41
71
|
**instance** of `MyWorker` and will execute inside its own `Thread`, so take
|
42
72
|
care when accessing other shared resources.
|
43
73
|
|
74
|
+
### STOMP-specific support
|
75
|
+
|
44
76
|
The consume block accepts the usual
|
45
77
|
[Stomp::Client](https://github.com/stompgem/stomp) subscription headers, as well
|
46
78
|
as :dead_letter_queue and :max\_redeliveries. If either of the latter two is
|
@@ -48,6 +80,7 @@ present, the consumer will unreceive any messages for which the block returns
|
|
48
80
|
false; after :max\_redeliveries, it will send the message to :dead_letter_queue.
|
49
81
|
`consume` blocks without these headers will fail silently rather than unreceive.
|
50
82
|
|
83
|
+
|
51
84
|
## Installation
|
52
85
|
|
53
86
|
Add this line to your application's Gemfile:
|
@@ -0,0 +1,91 @@
|
|
1
|
+
require 'jms'
|
2
|
+
require 'stapfen/destination'
|
3
|
+
|
4
|
+
module Stapfen
|
5
|
+
module Client
|
6
|
+
class JMS
|
7
|
+
attr_reader :connection
|
8
|
+
|
9
|
+
def initialize(configuration)
|
10
|
+
super()
|
11
|
+
@config = configuration
|
12
|
+
@connection = nil
|
13
|
+
end
|
14
|
+
|
15
|
+
# Connect to the broker via JMS and start the JMS session
|
16
|
+
#
|
17
|
+
# @return [JMS::Connection]
|
18
|
+
def connect(*args)
|
19
|
+
@connection = ::JMS::Connection.new(@config)
|
20
|
+
@connection.start
|
21
|
+
return @connection
|
22
|
+
end
|
23
|
+
|
24
|
+
# Accessor method which will cache the session if we've already created
|
25
|
+
# it once
|
26
|
+
#
|
27
|
+
# @return [JMS::Session] Instantiated +JMS::Session+ for our
|
28
|
+
# +connection+
|
29
|
+
def session
|
30
|
+
@session ||= connection.create_session
|
31
|
+
end
|
32
|
+
|
33
|
+
def publish(destination, body, headers={})
|
34
|
+
destination = Stapfen::Destination.from_string(destination)
|
35
|
+
|
36
|
+
session.producer(destination.jms_opts) do |p|
|
37
|
+
# Create the JMS typed Message
|
38
|
+
message = session.message(body)
|
39
|
+
|
40
|
+
message.delivery_mode = ::JMS::DeliveryMode::PERSISTENT if headers.delete(:persistent)
|
41
|
+
|
42
|
+
# Take the remainder of the headers and push them into the message
|
43
|
+
# properties.
|
44
|
+
headers.each_pair do |key, value|
|
45
|
+
message.setStringProperty(key.to_s, value.to_s)
|
46
|
+
end
|
47
|
+
|
48
|
+
p.send(message)
|
49
|
+
end
|
50
|
+
end
|
51
|
+
|
52
|
+
def subscribe(destination, headers={}, &block)
|
53
|
+
destination = Stapfen::Destination.from_string(destination)
|
54
|
+
connection.on_message(destination.jms_opts) do |m|
|
55
|
+
block.call(m)
|
56
|
+
end
|
57
|
+
end
|
58
|
+
|
59
|
+
# Close the JMS::Connection and the JMS::Session if it's been created
|
60
|
+
# for this client
|
61
|
+
#
|
62
|
+
# @return [Boolean] True/false depending on whether we actually closed
|
63
|
+
# the connection
|
64
|
+
def close
|
65
|
+
return false unless @connection
|
66
|
+
@session.close if @session
|
67
|
+
@connection.close
|
68
|
+
@connection = nil
|
69
|
+
return true
|
70
|
+
end
|
71
|
+
|
72
|
+
# API compatibilty method, doesn't actually indicate that the connection
|
73
|
+
# is closed. Will only return true if no connection currently exists
|
74
|
+
#
|
75
|
+
# @return [Boolean]
|
76
|
+
def closed?
|
77
|
+
return connection.nil?
|
78
|
+
end
|
79
|
+
|
80
|
+
def runloop
|
81
|
+
loop do
|
82
|
+
sleep 1
|
83
|
+
end
|
84
|
+
end
|
85
|
+
|
86
|
+
def can_unreceive?
|
87
|
+
false
|
88
|
+
end
|
89
|
+
end
|
90
|
+
end
|
91
|
+
end
|
@@ -0,0 +1,35 @@
|
|
1
|
+
require 'stomp'
|
2
|
+
|
3
|
+
module Stapfen
|
4
|
+
module Client
|
5
|
+
class Stomp < ::Stomp::Client
|
6
|
+
|
7
|
+
def initialize(config)
|
8
|
+
# Perform a deep-copy of the configuration since +Stomp::Client+ will
|
9
|
+
# mutate/mess up the configuration +Hash+ passed in here, see:
|
10
|
+
# <https://github.com/stompgem/stomp/issues/80>
|
11
|
+
super(Marshal.load(Marshal.dump(config)))
|
12
|
+
end
|
13
|
+
|
14
|
+
def connect(*args)
|
15
|
+
# No-op, since Stomp::Client will connect on instantiation
|
16
|
+
end
|
17
|
+
|
18
|
+
def can_unreceive?
|
19
|
+
true
|
20
|
+
end
|
21
|
+
|
22
|
+
def runloop
|
23
|
+
# Performing this join/runningloop to make sure that we don't
|
24
|
+
# experience potential deadlocks between signal handlers who might
|
25
|
+
# close the connection, and an infinite Client#join call
|
26
|
+
#
|
27
|
+
# Instead of using client#open? we use #running which will still be
|
28
|
+
# true even if the client is currently in an exponential reconnect loop
|
29
|
+
while self.running do
|
30
|
+
self.join(1)
|
31
|
+
end
|
32
|
+
end
|
33
|
+
end
|
34
|
+
end
|
35
|
+
end
|
data/lib/stapfen/destination.rb
CHANGED
@@ -20,6 +20,26 @@ module Stapfen
|
|
20
20
|
end
|
21
21
|
end
|
22
22
|
|
23
|
+
def as_jms
|
24
|
+
if queue?
|
25
|
+
return "queue://#{@name}"
|
26
|
+
end
|
27
|
+
|
28
|
+
if topic?
|
29
|
+
return "topic://#{@name}"
|
30
|
+
end
|
31
|
+
end
|
32
|
+
|
33
|
+
def jms_opts
|
34
|
+
if queue?
|
35
|
+
return {:queue_name => name}
|
36
|
+
end
|
37
|
+
|
38
|
+
if topic?
|
39
|
+
return {:topic_name => name}
|
40
|
+
end
|
41
|
+
end
|
42
|
+
|
23
43
|
# Create a {Stapfen::Destination} from the given string
|
24
44
|
#
|
25
45
|
# @param [String] name
|
data/lib/stapfen/logger.rb
CHANGED
@@ -18,7 +18,7 @@ module Stapfen
|
|
18
18
|
|
19
19
|
def proxy_log_method(method, arguments)
|
20
20
|
if self.logger
|
21
|
-
self.logger.send(method, *arguments)
|
21
|
+
self.logger.call.send(method, *arguments)
|
22
22
|
return true
|
23
23
|
end
|
24
24
|
return false
|
@@ -39,7 +39,7 @@ module Stapfen
|
|
39
39
|
|
40
40
|
def proxy_log_method(method, arguments)
|
41
41
|
if self.class.logger
|
42
|
-
self.class.logger.send(method, *arguments)
|
42
|
+
self.class.logger.call.send(method, *arguments)
|
43
43
|
return true
|
44
44
|
end
|
45
45
|
return false
|
data/lib/stapfen/message.rb
CHANGED
data/lib/stapfen/version.rb
CHANGED
data/lib/stapfen/worker.rb
CHANGED
@@ -11,12 +11,8 @@ module Stapfen
|
|
11
11
|
@@signals_handled = false
|
12
12
|
@@workers = []
|
13
13
|
|
14
|
-
# Class instance variables!
|
15
|
-
@use_stomp = true
|
16
|
-
|
17
14
|
class << self
|
18
15
|
attr_accessor :configuration, :consumers, :logger, :destructor
|
19
|
-
|
20
16
|
end
|
21
17
|
|
22
18
|
# Instantiate a new +Worker+ instance and run it
|
@@ -56,7 +52,7 @@ module Stapfen
|
|
56
52
|
end
|
57
53
|
|
58
54
|
def self.stomp?
|
59
|
-
@use_stomp
|
55
|
+
@use_stomp.nil? || @use_stomp
|
60
56
|
end
|
61
57
|
|
62
58
|
# Force the worker to use JMS as the messaging protocol.
|
@@ -82,13 +78,13 @@ module Stapfen
|
|
82
78
|
end
|
83
79
|
|
84
80
|
def self.jms?
|
85
|
-
!(
|
81
|
+
!(stomp?)
|
86
82
|
end
|
87
83
|
|
88
84
|
# Optional method, should be passed a block which will yield a {{Logger}}
|
89
85
|
# instance for the Stapfen worker to use
|
90
|
-
def self.log
|
91
|
-
@logger =
|
86
|
+
def self.log(&block)
|
87
|
+
@logger = block
|
92
88
|
end
|
93
89
|
|
94
90
|
# Main message consumption block
|
@@ -158,55 +154,17 @@ module Stapfen
|
|
158
154
|
|
159
155
|
def run
|
160
156
|
if self.class.stomp?
|
161
|
-
|
157
|
+
require 'stapfen/client/stomp'
|
158
|
+
@client = Stapfen::Client::Stomp.new(self.class.configuration.call)
|
162
159
|
elsif self.class.jms?
|
163
|
-
|
164
|
-
|
165
|
-
end
|
166
|
-
|
167
|
-
def run_jms
|
168
|
-
JMS::Connection.start(self.class.configuration.call) do |connection|
|
169
|
-
@client = connection
|
170
|
-
debug("Running with #{@client} inside of Thread:#{Thread.current.inspect}")
|
171
|
-
|
172
|
-
self.class.consumers.each do |name, headers, block|
|
173
|
-
destination = Stapfen::Destination.from_string(name)
|
174
|
-
type = 'queue'
|
175
|
-
options = {}
|
176
|
-
|
177
|
-
if destination.queue?
|
178
|
-
options[:queue_name] = destination.name
|
179
|
-
end
|
180
|
-
|
181
|
-
if destination.topic?
|
182
|
-
type = 'topic'
|
183
|
-
options[:topic_name] = destination.name
|
184
|
-
end
|
185
|
-
|
186
|
-
method_name = "handle_#{type}_#{name}".to_sym
|
187
|
-
self.class.send(:define_method, method_name, &block)
|
188
|
-
|
189
|
-
connection.on_message(options) do |m|
|
190
|
-
message = Stapfen::Message.from_jms(m)
|
191
|
-
self.send(method_name, message)
|
192
|
-
end
|
193
|
-
end
|
194
|
-
|
195
|
-
begin
|
196
|
-
loop do
|
197
|
-
sleep 1
|
198
|
-
end
|
199
|
-
debug("Exiting the JMS runloop for #{self}")
|
200
|
-
rescue Interrupt
|
201
|
-
exit_cleanly
|
202
|
-
end
|
160
|
+
require 'stapfen/client/jms'
|
161
|
+
@client = Stapfen::Client::JMS.new(self.class.configuration.call)
|
203
162
|
end
|
204
|
-
end
|
205
163
|
|
206
|
-
def run_stomp
|
207
|
-
@client = Stomp::Client.new(self.class.configuration.call)
|
208
164
|
debug("Running with #{@client} inside of Thread:#{Thread.current.inspect}")
|
209
165
|
|
166
|
+
@client.connect
|
167
|
+
|
210
168
|
self.class.consumers.each do |name, headers, block|
|
211
169
|
unreceive_headers = {}
|
212
170
|
[:max_redeliveries, :dead_letter_queue].each do |sym|
|
@@ -219,25 +177,28 @@ module Stapfen
|
|
219
177
|
method_name = name.gsub(/[.|\-]/, '_').to_sym
|
220
178
|
self.class.send(:define_method, method_name, &block)
|
221
179
|
|
222
|
-
client.subscribe(name, headers) do |
|
180
|
+
client.subscribe(name, headers) do |m|
|
181
|
+
message = nil
|
182
|
+
if self.class.stomp?
|
183
|
+
message = Stapfen::Message.from_stomp(m)
|
184
|
+
end
|
185
|
+
|
186
|
+
if self.class.jms?
|
187
|
+
message = Stapfen::Message.from_jms(m)
|
188
|
+
end
|
189
|
+
|
223
190
|
success = self.send(method_name, message)
|
224
191
|
|
225
|
-
|
226
|
-
client.
|
192
|
+
unless success
|
193
|
+
if client.can_unreceive? && !unreceive_headers.empty?
|
194
|
+
client.unreceive(m, unreceive_headers)
|
195
|
+
end
|
227
196
|
end
|
228
197
|
end
|
229
198
|
end
|
230
199
|
|
231
200
|
begin
|
232
|
-
|
233
|
-
# experience potential deadlocks between signal handlers who might
|
234
|
-
# close the connection, and an infinite Client#join call
|
235
|
-
#
|
236
|
-
# Instead of using client#open? we use #running which will still be
|
237
|
-
# true even if the client is currently in an exponential reconnect loop
|
238
|
-
while client.running do
|
239
|
-
client.join(1)
|
240
|
-
end
|
201
|
+
client.runloop
|
241
202
|
warn("Exiting the runloop for #{self}")
|
242
203
|
rescue Interrupt
|
243
204
|
exit_cleanly
|
@@ -251,8 +212,10 @@ module Stapfen
|
|
251
212
|
self.class.destructor.call if self.class.destructor
|
252
213
|
|
253
214
|
# Only close the client if we have one sitting around
|
254
|
-
if client
|
255
|
-
client.
|
215
|
+
if client
|
216
|
+
unless client.closed?
|
217
|
+
client.close
|
218
|
+
end
|
256
219
|
end
|
257
220
|
end
|
258
221
|
end
|
data/lib/stapfen.rb
CHANGED
@@ -1,4 +1,19 @@
|
|
1
|
+
begin
|
2
|
+
require 'stomp'
|
3
|
+
rescue LoadError
|
4
|
+
# Can't process Stomp
|
5
|
+
end
|
6
|
+
|
7
|
+
begin
|
8
|
+
require 'java'
|
9
|
+
require 'jms'
|
10
|
+
rescue LoadError
|
11
|
+
# Can't process JMS
|
12
|
+
end
|
13
|
+
|
14
|
+
|
1
15
|
require 'stapfen/version'
|
16
|
+
require 'stapfen/client'
|
2
17
|
require 'stapfen/worker'
|
3
18
|
|
4
19
|
module Stapfen
|
@@ -0,0 +1,106 @@
|
|
1
|
+
require 'spec_helper'
|
2
|
+
|
3
|
+
if RUBY_PLATFORM == 'java'
|
4
|
+
require 'stapfen/client/jms'
|
5
|
+
|
6
|
+
describe Stapfen::Client::JMS, :java => true do
|
7
|
+
let(:config) { {} }
|
8
|
+
subject(:client) { described_class.new(config) }
|
9
|
+
|
10
|
+
it { should respond_to :connect }
|
11
|
+
|
12
|
+
describe '#can_unreceive?' do
|
13
|
+
subject { client.can_unreceive? }
|
14
|
+
|
15
|
+
it { should_not be_true }
|
16
|
+
end
|
17
|
+
|
18
|
+
describe '#connect' do
|
19
|
+
subject(:connection) { client.connect }
|
20
|
+
let(:jms_conn) { double('JMS::Connection') }
|
21
|
+
|
22
|
+
before :each do
|
23
|
+
::JMS::Connection.should_receive(:new).and_return(jms_conn)
|
24
|
+
end
|
25
|
+
|
26
|
+
it 'should start the connection' do
|
27
|
+
jms_conn.should_receive(:start)
|
28
|
+
expect(connection).to eql(jms_conn)
|
29
|
+
end
|
30
|
+
end
|
31
|
+
|
32
|
+
describe '#session' do
|
33
|
+
let(:session) { double('JMS::Session') }
|
34
|
+
let(:connection) { double('JMS::Connection') }
|
35
|
+
|
36
|
+
before :each do
|
37
|
+
client.stub(:connection => connection)
|
38
|
+
end
|
39
|
+
|
40
|
+
context 'without a session already' do
|
41
|
+
it 'should create a new session' do
|
42
|
+
connection.should_receive(:create_session).and_return(session)
|
43
|
+
expect(client.session).to eql(session)
|
44
|
+
end
|
45
|
+
end
|
46
|
+
|
47
|
+
context 'with an existing session' do
|
48
|
+
it 'should return that existing session' do
|
49
|
+
connection.should_receive(:create_session).once.and_return(session)
|
50
|
+
3.times do
|
51
|
+
expect(client.session).to eql(session)
|
52
|
+
end
|
53
|
+
end
|
54
|
+
end
|
55
|
+
end
|
56
|
+
|
57
|
+
describe '#publish' do
|
58
|
+
end
|
59
|
+
|
60
|
+
describe '#closed?' do
|
61
|
+
subject(:result) { client.closed? }
|
62
|
+
|
63
|
+
context 'if a connection exists' do
|
64
|
+
before :each do
|
65
|
+
client.stub(:connection).and_return(double('JMS::Connection'))
|
66
|
+
end
|
67
|
+
|
68
|
+
it { should be_false }
|
69
|
+
end
|
70
|
+
|
71
|
+
context 'without a connection' do
|
72
|
+
it { should be_true }
|
73
|
+
end
|
74
|
+
end
|
75
|
+
|
76
|
+
describe '#close' do
|
77
|
+
subject(:result) { client.close }
|
78
|
+
let(:connection) { double('JMS::Connection') }
|
79
|
+
|
80
|
+
before :each do
|
81
|
+
client.instance_variable_set(:@connection, connection)
|
82
|
+
end
|
83
|
+
|
84
|
+
context 'without an existing session' do
|
85
|
+
it 'should close the client' do
|
86
|
+
connection.should_receive(:close)
|
87
|
+
expect(result).to be_true
|
88
|
+
end
|
89
|
+
end
|
90
|
+
|
91
|
+
context 'with an existing session' do
|
92
|
+
let(:session) { double('JMS::Session') }
|
93
|
+
|
94
|
+
before :each do
|
95
|
+
client.instance_variable_set(:@session, session)
|
96
|
+
end
|
97
|
+
|
98
|
+
it 'should close the client and session' do
|
99
|
+
session.should_receive(:close)
|
100
|
+
connection.should_receive(:close)
|
101
|
+
expect(result).to be_true
|
102
|
+
end
|
103
|
+
end
|
104
|
+
end
|
105
|
+
end
|
106
|
+
end
|
data/spec/client_spec.rb
ADDED
data/spec/destination_spec.rb
CHANGED
@@ -5,6 +5,19 @@ describe Stapfen::Destination do
|
|
5
5
|
it { should respond_to :name }
|
6
6
|
it { should respond_to :type }
|
7
7
|
|
8
|
+
describe '#as_jms' do
|
9
|
+
let(:name) { 'rspec/dlq' }
|
10
|
+
subject(:destination) do
|
11
|
+
d = described_class.new
|
12
|
+
d.type = :queue
|
13
|
+
d.name = name
|
14
|
+
d.as_jms
|
15
|
+
end
|
16
|
+
|
17
|
+
it { should be_instance_of String }
|
18
|
+
it { should eql "queue://#{name}" }
|
19
|
+
end
|
20
|
+
|
8
21
|
describe '#as_stomp' do
|
9
22
|
let(:name) { 'rspec/dlq' }
|
10
23
|
|
data/spec/logger_spec.rb
CHANGED
data/spec/worker_spec.rb
CHANGED
@@ -38,6 +38,22 @@ describe Stapfen::Worker do
|
|
38
38
|
end
|
39
39
|
end
|
40
40
|
|
41
|
+
describe '#log' do
|
42
|
+
it "should store the block it's passed" do
|
43
|
+
logger = double('Mock Logger')
|
44
|
+
|
45
|
+
worker.log do
|
46
|
+
logger
|
47
|
+
end
|
48
|
+
|
49
|
+
expect(worker.logger).to be_instance_of Proc
|
50
|
+
end
|
51
|
+
|
52
|
+
after :each do
|
53
|
+
worker.logger = nil
|
54
|
+
end
|
55
|
+
end
|
56
|
+
|
41
57
|
describe '#configure' do
|
42
58
|
it 'should error when not passed a block' do
|
43
59
|
expect {
|
@@ -52,11 +68,10 @@ describe Stapfen::Worker do
|
|
52
68
|
config
|
53
69
|
end
|
54
70
|
|
55
|
-
worker.configuration.call.
|
71
|
+
expect(worker.configuration.call).to eql(config)
|
56
72
|
end
|
57
73
|
end
|
58
74
|
|
59
|
-
|
60
75
|
describe '#exit_cleanly' do
|
61
76
|
subject(:result) { worker.exit_cleanly }
|
62
77
|
|
@@ -120,14 +135,28 @@ describe Stapfen::Worker do
|
|
120
135
|
end
|
121
136
|
|
122
137
|
context 'unreceive behavior' do
|
123
|
-
let(:client)
|
138
|
+
let(:client) do
|
139
|
+
c = double('Mock Stapfen::Client')
|
140
|
+
c.stub(:connect)
|
141
|
+
c.stub(:can_unreceive? => true)
|
142
|
+
c.stub(:runloop)
|
143
|
+
c
|
144
|
+
end
|
145
|
+
|
124
146
|
let(:name) { '/queue/some_queue' }
|
147
|
+
let(:message) do
|
148
|
+
m = Stomp::Message.new(nil)
|
149
|
+
m.stub(:body => 'rspec msg')
|
150
|
+
m
|
151
|
+
end
|
152
|
+
|
153
|
+
|
125
154
|
before :each do
|
126
|
-
|
155
|
+
Stapfen::Client::Stomp.stub(:new).and_return(client)
|
127
156
|
|
128
157
|
# Get a subscription? Call the message handler block.
|
129
158
|
client.stub(:subscribe) do |name, headers, &block|
|
130
|
-
block.call(
|
159
|
+
block.call(message)
|
131
160
|
end
|
132
161
|
end
|
133
162
|
|
@@ -164,7 +193,7 @@ describe Stapfen::Worker do
|
|
164
193
|
worker.new.run
|
165
194
|
end
|
166
195
|
it 'should pass :unreceive_headers through to the unreceive call' do
|
167
|
-
client.should_receive(:unreceive).with(
|
196
|
+
client.should_receive(:unreceive).with(message, unrec_headers).once
|
168
197
|
|
169
198
|
worker.consume(name, raw_headers) {|msg| false }
|
170
199
|
worker.new.run
|
metadata
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: stapfen
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version:
|
4
|
+
version: 2.0.0
|
5
5
|
prerelease:
|
6
6
|
platform: ruby
|
7
7
|
authors:
|
@@ -9,7 +9,7 @@ authors:
|
|
9
9
|
autorequire:
|
10
10
|
bindir: bin
|
11
11
|
cert_chain: []
|
12
|
-
date: 2013-
|
12
|
+
date: 2013-10-03 00:00:00.000000000 Z
|
13
13
|
dependencies: []
|
14
14
|
description: A simple gem for writing good basic STOMP workers
|
15
15
|
email:
|
@@ -19,6 +19,7 @@ extensions: []
|
|
19
19
|
extra_rdoc_files: []
|
20
20
|
files:
|
21
21
|
- .gitignore
|
22
|
+
- CHANGES.md
|
22
23
|
- Gemfile
|
23
24
|
- Guardfile
|
24
25
|
- LICENSE.txt
|
@@ -26,11 +27,17 @@ files:
|
|
26
27
|
- Rakefile
|
27
28
|
- examples/simple.rb
|
28
29
|
- lib/stapfen.rb
|
30
|
+
- lib/stapfen/client.rb
|
31
|
+
- lib/stapfen/client/jms.rb
|
32
|
+
- lib/stapfen/client/stomp.rb
|
29
33
|
- lib/stapfen/destination.rb
|
30
34
|
- lib/stapfen/logger.rb
|
31
35
|
- lib/stapfen/message.rb
|
32
36
|
- lib/stapfen/version.rb
|
33
37
|
- lib/stapfen/worker.rb
|
38
|
+
- spec/client/jms_spec.rb
|
39
|
+
- spec/client/stomp_spec.rb
|
40
|
+
- spec/client_spec.rb
|
34
41
|
- spec/destination_spec.rb
|
35
42
|
- spec/logger_spec.rb
|
36
43
|
- spec/message_spec.rb
|
@@ -51,7 +58,7 @@ required_ruby_version: !ruby/object:Gem::Requirement
|
|
51
58
|
version: '0'
|
52
59
|
segments:
|
53
60
|
- 0
|
54
|
-
hash:
|
61
|
+
hash: 497669016429276389
|
55
62
|
required_rubygems_version: !ruby/object:Gem::Requirement
|
56
63
|
none: false
|
57
64
|
requirements:
|
@@ -60,7 +67,7 @@ required_rubygems_version: !ruby/object:Gem::Requirement
|
|
60
67
|
version: '0'
|
61
68
|
segments:
|
62
69
|
- 0
|
63
|
-
hash:
|
70
|
+
hash: 497669016429276389
|
64
71
|
requirements: []
|
65
72
|
rubyforge_project:
|
66
73
|
rubygems_version: 1.8.25
|
@@ -68,6 +75,9 @@ signing_key:
|
|
68
75
|
specification_version: 3
|
69
76
|
summary: A simple gem for writing good basic STOMP workers
|
70
77
|
test_files:
|
78
|
+
- spec/client/jms_spec.rb
|
79
|
+
- spec/client/stomp_spec.rb
|
80
|
+
- spec/client_spec.rb
|
71
81
|
- spec/destination_spec.rb
|
72
82
|
- spec/logger_spec.rb
|
73
83
|
- spec/message_spec.rb
|