shoryuken 0.0.5 → 1.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.
@@ -1,62 +1,21 @@
1
1
  require 'spec_helper'
2
2
 
3
3
  describe Shoryuken::Client do
4
- let(:sqs) { double 'SQS' }
5
- let(:queue_collection) { double 'Queues Collection' }
6
- let(:sqs_queue) { double 'SQS Queue' }
7
- let(:queue) { 'shoryuken' }
4
+ let(:credentials) { Aws::Credentials.new('access_key_id', 'secret_access_key') }
5
+ let(:sqs) { Aws::SQS::Client.new(stub_responses: true, credentials: credentials) }
6
+ let(:queue_name) { 'shoryuken' }
7
+ let(:queue_url) { 'https://eu-west-1.amazonaws.com:6059/123456789012/shoryuken' }
8
8
 
9
9
  before do
10
- allow(described_class).to receive(:sqs).and_return(sqs)
11
- allow(sqs).to receive(:queues).and_return(queue_collection)
12
- allow(queue_collection).to receive(:named).and_return(sqs_queue)
10
+ described_class.sqs = sqs
13
11
  end
14
12
 
15
- describe '.queues' do
13
+ describe '.queue' do
16
14
  it 'memoizes queues' do
17
- expect(queue_collection).to receive(:named).once.with(queue).and_return(sqs_queue)
15
+ sqs.stub_responses(:get_queue_url, { queue_url: queue_url }, { queue_url: 'xyz' })
18
16
 
19
- expect(Shoryuken::Client.queues(queue)).to eq sqs_queue
20
- expect(Shoryuken::Client.queues(queue)).to eq sqs_queue
21
- end
22
- end
23
-
24
- describe '.send_message' do
25
- it 'enqueues a message' do
26
- expect(sqs_queue).to receive(:send_message).with('test', {})
27
-
28
- described_class.send_message(queue, 'test')
29
- end
30
-
31
- it 'enqueues a message with options' do
32
- expect(sqs_queue).to receive(:send_message).with('test2', delay_seconds: 60)
33
-
34
- described_class.send_message(queue, 'test2', delay_seconds: 60)
35
- end
36
-
37
- it 'parsers as JSON by default' do
38
- msg = { field: 'test', other_field: 'other' }
39
-
40
- expect(sqs_queue).to receive(:send_message).with(JSON.dump(msg), {})
41
-
42
- described_class.send_message(queue, msg)
43
- end
44
-
45
- it 'parsers as JSON by default and keep the options' do
46
- msg = { field: 'test', other_field: 'other' }
47
-
48
- expect(sqs_queue).to receive(:send_message).with(JSON.dump(msg), { delay_seconds: 60 })
49
-
50
- described_class.send_message(queue, msg, delay_seconds: 60)
51
- end
52
- end
53
-
54
- describe '.visibility_timeout' do
55
- it 'memoizes visibility_timeout' do
56
- expect(sqs_queue).to receive(:visibility_timeout).once.and_return(30)
57
-
58
- expect(Shoryuken::Client.visibility_timeout(queue)).to eq 30
59
- expect(Shoryuken::Client.visibility_timeout(queue)).to eq 30
17
+ expect(Shoryuken::Client.queues(queue_name).url).to eq queue_url
18
+ expect(Shoryuken::Client.queues(queue_name).url).to eq queue_url
60
19
  end
61
20
  end
62
21
  end
@@ -48,7 +48,7 @@ describe Shoryuken::DefaultWorkerRegistry do
48
48
  string_value: explicit_worker.to_s,
49
49
  data_type: 'String' } if explicit_worker
50
50
 
51
- double AWS::SQS::ReceivedMessage,
51
+ double Aws::SQS::Message,
52
52
  body: 'test',
53
53
  message_attributes: attributes,
54
54
  message_id: SecureRandom.uuid
@@ -3,62 +3,68 @@ require 'shoryuken/manager'
3
3
  require 'shoryuken/fetcher'
4
4
 
5
5
  describe Shoryuken::Fetcher do
6
- let(:manager) { double Shoryuken::Manager }
7
- let(:sqs_queue) { double 'sqs_queue' }
8
- let(:queue) { 'default' }
9
- let(:sqs_msg) { double AWS::SQS::ReceivedMessage, id: 'fc754df7-9cc2-4c41-96ca-5996a44b771e', body: 'test' }
6
+ let(:manager) { double Shoryuken::Manager }
7
+ let(:queue) { double Aws::SQS::Queue }
8
+ let(:queue_name) { 'default' }
9
+
10
+ let(:sqs_msg) do
11
+ double Aws::SQS::Message,
12
+ queue_url: queue_name,
13
+ body: 'test',
14
+ message_id: 'fc754df7-9cc2-4c41-96ca-5996a44b771e'
15
+ end
10
16
 
11
17
  subject { described_class.new(manager) }
12
18
 
13
19
  before do
14
20
  allow(manager).to receive(:async).and_return(manager)
15
- allow(Shoryuken::Client).to receive(:queues).with(queue).and_return(sqs_queue)
21
+ allow(Shoryuken::Client).to receive(:queues).with(queue_name).and_return(queue)
16
22
  end
17
23
 
18
24
 
19
25
  describe '#fetch' do
20
26
  it 'calls pause when no message' do
21
- allow(sqs_queue).to receive(:receive_message).with(limit: 1, message_attribute_names: ['shoryuken_class']).and_return([])
27
+ allow(queue).to receive(:receive_messages).with(max_number_of_messages: 1, message_attribute_names: ['All']).and_return([])
22
28
 
23
- expect(manager).to receive(:pause_queue!).with(queue)
29
+ expect(manager).to receive(:pause_queue!).with(queue_name)
24
30
  expect(manager).to receive(:dispatch)
25
31
 
26
- subject.fetch(queue, 1)
32
+ subject.fetch(queue_name, 1)
27
33
  end
28
34
 
29
35
  it 'assigns messages' do
30
- allow(sqs_queue).to receive(:receive_message).with(limit: 5, message_attribute_names: ['shoryuken_class']).and_return(sqs_msg)
36
+ allow(queue).to receive(:receive_messages).with(max_number_of_messages: 5, message_attribute_names: ['All']).and_return(sqs_msg)
31
37
 
32
- expect(manager).to receive(:rebalance_queue_weight!).with(queue)
33
- expect(manager).to receive(:assign).with(queue, sqs_msg)
38
+ expect(manager).to receive(:rebalance_queue_weight!).with(queue_name)
39
+ expect(manager).to receive(:assign).with(queue_name, sqs_msg)
34
40
  expect(manager).to receive(:dispatch)
35
41
 
36
- subject.fetch(queue, 5)
42
+ subject.fetch(queue_name, 5)
37
43
  end
38
44
 
39
45
  it 'assigns messages in batch' do
40
46
  TestWorker.get_shoryuken_options['batch'] = true
41
47
 
42
- allow(sqs_queue).to receive(:receive_message).with(limit: described_class::FETCH_LIMIT, message_attribute_names: ['shoryuken_class']).and_return(sqs_msg)
48
+ allow(queue).to receive(:receive_messages).with(max_number_of_messages: described_class::FETCH_LIMIT, message_attribute_names: ['All']).and_return(sqs_msg)
43
49
 
44
- expect(manager).to receive(:rebalance_queue_weight!).with(queue)
45
- expect(manager).to receive(:assign).with(queue, [sqs_msg])
50
+ expect(manager).to receive(:rebalance_queue_weight!).with(queue_name)
51
+ expect(manager).to receive(:assign).with(queue_name, [sqs_msg])
46
52
  expect(manager).to receive(:dispatch)
47
53
 
48
- subject.fetch(queue, 5)
54
+ subject.fetch(queue_name, 5)
49
55
  end
50
56
 
51
57
  context 'when worker not found' do
52
- let(:queue) { 'notfound' }
58
+ let(:queue_name) { 'notfound' }
53
59
 
54
60
  it 'ignores batch' do
55
- allow(sqs_queue).to receive(:receive_message).with(limit: 5, message_attribute_names: ['shoryuken_class']).and_return(sqs_msg)
61
+ allow(queue).to receive(:receive_messages).with(max_number_of_messages: 5, message_attribute_names: ['All']).and_return(sqs_msg)
56
62
 
57
- expect(manager).to receive(:rebalance_queue_weight!).with(queue)
58
- expect(manager).to receive(:assign).with(queue, sqs_msg)
63
+ expect(manager).to receive(:rebalance_queue_weight!).with(queue_name)
64
+ expect(manager).to receive(:assign).with(queue_name, sqs_msg)
59
65
  expect(manager).to receive(:dispatch)
60
66
 
61
- subject.fetch(queue, 5)
67
+ subject.fetch(queue_name, 5)
62
68
  end
63
69
  end
64
70
  end
@@ -1,9 +1,17 @@
1
1
  require 'spec_helper'
2
2
 
3
3
  describe Shoryuken::Middleware::Server::AutoDelete do
4
- let(:sqs_msg) { double AWS::SQS::ReceivedMessage, id: 'fc754df7-9cc2-4c41-96ca-5996a44b771e', body: 'test' }
5
4
  let(:queue) { 'default' }
6
- let(:sqs_queue) { double AWS::SQS::Queue }
5
+ let(:sqs_queue) { double Aws::SQS::Queue }
6
+
7
+ def build_message
8
+ double Aws::SQS::Message,
9
+ queue_url: queue,
10
+ body: 'test',
11
+ receipt_handle: SecureRandom.uuid
12
+ end
13
+
14
+ let(:sqs_msg) { build_message }
7
15
 
8
16
  before do
9
17
  allow(Shoryuken::Client).to receive(:queues).with(queue).and_return(sqs_queue)
@@ -12,7 +20,8 @@ describe Shoryuken::Middleware::Server::AutoDelete do
12
20
  it 'deletes a message' do
13
21
  TestWorker.get_shoryuken_options['auto_delete'] = true
14
22
 
15
- expect(sqs_queue).to receive(:batch_delete).with(sqs_msg)
23
+ expect(sqs_queue).to receive(:delete_messages).with(entries: [
24
+ { id: '0', receipt_handle: sqs_msg.receipt_handle }])
16
25
 
17
26
  subject.call(TestWorker.new, queue, sqs_msg, sqs_msg.body) {}
18
27
  end
@@ -20,12 +29,15 @@ describe Shoryuken::Middleware::Server::AutoDelete do
20
29
  it 'deletes a batch' do
21
30
  TestWorker.get_shoryuken_options['auto_delete'] = true
22
31
 
23
- sqs_msg2 = double 'SQS msg', body: 'test'
24
- sqs_msg3 = double 'SQS msg', body: 'test'
32
+ sqs_msg2 = build_message
33
+ sqs_msg3 = build_message
25
34
 
26
35
  sqs_msgs = [sqs_msg, sqs_msg2, sqs_msg3]
27
36
 
28
- expect(sqs_queue).to receive(:batch_delete).with(*sqs_msgs)
37
+ expect(sqs_queue).to receive(:delete_messages).with(entries: [
38
+ { id: '0', receipt_handle: sqs_msg.receipt_handle },
39
+ { id: '1', receipt_handle: sqs_msg2.receipt_handle },
40
+ { id: '2', receipt_handle: sqs_msg3.receipt_handle }])
29
41
 
30
42
  subject.call(TestWorker.new, queue, sqs_msgs, [sqs_msg.body, sqs_msg2.body, sqs_msg3.body]) {}
31
43
  end
@@ -33,14 +45,14 @@ describe Shoryuken::Middleware::Server::AutoDelete do
33
45
  it 'does not delete a message' do
34
46
  TestWorker.get_shoryuken_options['auto_delete'] = false
35
47
 
36
- expect(sqs_queue).to_not receive(:batch_delete)
48
+ expect(sqs_queue).to_not receive(:delete_messages)
37
49
 
38
50
  subject.call(TestWorker.new, queue, sqs_msg, sqs_msg.body) {}
39
51
  end
40
52
 
41
53
  context 'when exception' do
42
54
  it 'does not delete a message' do
43
- expect(sqs_queue).to_not receive(:batch_delete)
55
+ expect(sqs_queue).to_not receive(:delete_messages)
44
56
 
45
57
  expect {
46
58
  subject.call(TestWorker.new, queue, sqs_msg, sqs_msg.body) { raise }
@@ -1,10 +1,21 @@
1
1
  require 'spec_helper'
2
2
 
3
3
  describe Shoryuken::Middleware::Server::Timing do
4
- let(:sqs_msg) { double AWS::SQS::ReceivedMessage, id: 'fc754df7-9cc2-4c41-96ca-5996a44b771e', body: 'test' }
5
- let(:queue) { 'default' }
4
+ let(:queue) { 'default' }
5
+ let(:sqs_queue) { double Aws::SQS::Queue, visibility_timeout: 60 }
6
+
7
+ let(:sqs_msg) do
8
+ double Aws::SQS::Message,
9
+ queue_url: queue,
10
+ body: 'test',
11
+ message_id: 'fc754df7-9cc2-4c41-96ca-5996a44b771e'
12
+ end
13
+
14
+ before do
15
+ allow(Shoryuken::Client).to receive(:queues).with(queue).and_return(sqs_queue)
16
+ end
6
17
 
7
- xit 'logs timing' do
18
+ it 'logs timing' do
8
19
  expect(Shoryuken.logger).to receive(:info).with(/started at/)
9
20
  expect(Shoryuken.logger).to receive(:info).with(/completed in/)
10
21
 
@@ -13,7 +24,6 @@ describe Shoryuken::Middleware::Server::Timing do
13
24
 
14
25
  context 'when exceeded the `visibility_timeout`' do
15
26
  it 'logs exceeded' do
16
- allow(Shoryuken::Client).to receive(:visibility_timeout).and_return(60)
17
27
  allow(subject).to receive(:elapsed).and_return(120000)
18
28
 
19
29
  expect(Shoryuken.logger).to receive(:info).with(/started at/)
@@ -4,9 +4,17 @@ require 'shoryuken/manager'
4
4
 
5
5
  describe Shoryuken::Processor do
6
6
  let(:manager) { double Shoryuken::Manager, processor_done: nil }
7
- let(:sqs_queue) { double AWS::SQS::Queue, visibility_timeout: 30 }
7
+ let(:sqs_queue) { double Aws::SQS::Queue, visibility_timeout: 30 }
8
8
  let(:queue) { 'default' }
9
- let(:sqs_msg) { double AWS::SQS::ReceivedMessage, id: 'fc754df7-9cc2-4c41-96ca-5996a44b771e', body: 'test', message_attributes: {} }
9
+
10
+ let(:sqs_msg) do
11
+ double Aws::SQS::Message,
12
+ queue_url: queue,
13
+ body: 'test',
14
+ message_attributes: {},
15
+ message_id: SecureRandom.uuid,
16
+ receipt_handle: SecureRandom.uuid
17
+ end
10
18
 
11
19
  subject { described_class.new(manager) }
12
20
 
@@ -110,29 +118,66 @@ describe Shoryuken::Processor do
110
118
 
111
119
  def perform(sqs_msg, body); end
112
120
  end
121
+ end
113
122
 
114
- Shoryuken.configure_server do |config|
115
- config.server_middleware do |chain|
116
- chain.add WorkerCalledMiddleware
123
+ context 'server' do
124
+ before do
125
+ allow(Shoryuken).to receive(:server?).and_return(true)
126
+ WorkerCalledMiddlewareWorker.instance_variable_set(:@server_chain, nil) # un-memoize middleware
127
+
128
+ Shoryuken.configure_server do |config|
129
+ config.server_middleware do |chain|
130
+ chain.add WorkerCalledMiddleware
131
+ end
117
132
  end
118
133
  end
119
- end
120
134
 
121
- after do
122
- Shoryuken.configure_server do |config|
123
- config.server_middleware do |chain|
124
- chain.remove WorkerCalledMiddleware
135
+ after do
136
+ Shoryuken.configure_server do |config|
137
+ config.server_middleware do |chain|
138
+ chain.remove WorkerCalledMiddleware
139
+ end
125
140
  end
126
141
  end
142
+
143
+ it 'invokes middleware' do
144
+ expect(manager).to receive(:processor_done).with(queue, subject)
145
+
146
+ expect_any_instance_of(WorkerCalledMiddlewareWorker).to receive(:perform).with(sqs_msg, sqs_msg.body)
147
+ expect_any_instance_of(WorkerCalledMiddlewareWorker).to receive(:called).with(sqs_msg, queue)
148
+
149
+ subject.process(queue, sqs_msg)
150
+ end
127
151
  end
128
152
 
129
- it 'invokes middleware' do
130
- expect(manager).to receive(:processor_done).with(queue, subject)
153
+ context 'client' do
154
+ before do
155
+ allow(Shoryuken).to receive(:server?).and_return(false)
156
+ WorkerCalledMiddlewareWorker.instance_variable_set(:@server_chain, nil) # un-memoize middleware
131
157
 
132
- expect_any_instance_of(WorkerCalledMiddlewareWorker).to receive(:perform).with(sqs_msg, sqs_msg.body)
133
- expect_any_instance_of(WorkerCalledMiddlewareWorker).to receive(:called).with(sqs_msg, queue)
158
+ Shoryuken.configure_server do |config|
159
+ config.server_middleware do |chain|
160
+ chain.add WorkerCalledMiddleware
161
+ end
162
+ end
163
+ end
134
164
 
135
- subject.process(queue, sqs_msg)
165
+ after do
166
+ Shoryuken.configure_server do |config|
167
+ config.server_middleware do |chain|
168
+ chain.remove WorkerCalledMiddleware
169
+ end
170
+ end
171
+ end
172
+
173
+ it "doesn't invoke middleware" do
174
+ expect(manager).to receive(:processor_done).with(queue, subject)
175
+
176
+ expect_any_instance_of(WorkerCalledMiddlewareWorker).to receive(:perform).with(sqs_msg, sqs_msg.body)
177
+ expect_any_instance_of(WorkerCalledMiddlewareWorker).to_not receive(:called).with(sqs_msg, queue)
178
+
179
+ subject.process(queue, sqs_msg)
180
+ end
136
181
  end
137
182
  end
138
183
 
@@ -143,7 +188,7 @@ describe Shoryuken::Processor do
143
188
 
144
189
  expect_any_instance_of(TestWorker).to receive(:perform).with(sqs_msg, sqs_msg.body)
145
190
 
146
- expect(sqs_queue).to receive(:batch_delete).with(sqs_msg)
191
+ expect(sqs_queue).to receive(:delete_messages).with(entries: [{ id: '0', receipt_handle: sqs_msg.receipt_handle }])
147
192
 
148
193
  subject.process(queue, sqs_msg)
149
194
  end
@@ -155,18 +200,23 @@ describe Shoryuken::Processor do
155
200
 
156
201
  expect_any_instance_of(TestWorker).to receive(:perform).with(sqs_msg, sqs_msg.body)
157
202
 
158
- expect(sqs_queue).to_not receive(:batch_delete)
203
+ expect(sqs_queue).to_not receive(:delete_messages)
159
204
 
160
205
  subject.process(queue, sqs_msg)
161
206
  end
162
207
 
163
208
  context 'when shoryuken_class header' do
164
- let(:sqs_msg) { double AWS::SQS::ReceivedMessage, id: 'fc754df7-9cc2-4c41-96ca-5996a44b771e', body: 'test', message_attributes: {
165
- 'shoryuken_class' => {
166
- string_value: TestWorker.to_s,
167
- data_type: 'String'
168
- }
169
- } }
209
+ let(:sqs_msg) do
210
+ double Aws::SQS::Message,
211
+ queue_url: queue,
212
+ body: 'test',
213
+ message_attributes: {
214
+ 'shoryuken_class' => {
215
+ string_value: TestWorker.to_s,
216
+ data_type: 'String' }},
217
+ message_id: SecureRandom.uuid,
218
+ receipt_handle: SecureRandom.uuid
219
+ end
170
220
 
171
221
  it 'performs without delete' do
172
222
  Shoryuken.worker_registry.clear # unregister TestWorker
@@ -175,7 +225,7 @@ describe Shoryuken::Processor do
175
225
 
176
226
  expect_any_instance_of(TestWorker).to receive(:perform).with(sqs_msg, sqs_msg.body)
177
227
 
178
- expect(sqs_queue).to_not receive(:batch_delete)
228
+ expect(sqs_queue).to_not receive(:delete_messages)
179
229
 
180
230
  subject.process(queue, sqs_msg)
181
231
  end
@@ -0,0 +1,42 @@
1
+ require 'spec_helper'
2
+
3
+ describe Shoryuken::SnsArn do
4
+ let(:account_id) { '1234567890' }
5
+ let(:region) { 'eu-west-1' }
6
+ let(:topic) { 'topic-x' }
7
+
8
+ before do
9
+ Shoryuken::Client.account_id = account_id
10
+ Aws.config = { region: region }
11
+ end
12
+
13
+ subject { described_class.new(topic).to_s }
14
+
15
+ describe '#to_s' do
16
+ context 'when the Aws config includes all the information necessary' do
17
+ it 'generates an SNS arn' do
18
+ expect(subject).to eq('arn:aws:sns:eu-west-1:1234567890:topic-x')
19
+ end
20
+ end
21
+
22
+ context 'when the Aws config does not include the account id' do
23
+ before do
24
+ Shoryuken::Client.account_id = nil
25
+ end
26
+
27
+ it 'fails' do
28
+ expect { subject }.to raise_error(/an :account_id/)
29
+ end
30
+ end
31
+
32
+ context 'when the Aws config does not include the region' do
33
+ before do
34
+ Aws.config.delete :region
35
+ end
36
+
37
+ it 'fails' do
38
+ expect { subject }.to raise_error(/a :region/)
39
+ end
40
+ end
41
+ end
42
+ end