alephant-publisher-queue 2.0.0 → 2.0.1
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.
- checksums.yaml +4 -4
- data/.gitignore +1 -0
- data/Gemfile +0 -1
- data/alephant-publisher-queue.gemspec +1 -2
- data/lib/alephant/publisher/queue/options.rb +5 -3
- data/lib/alephant/publisher/queue/processor/base.rb +3 -3
- data/lib/alephant/publisher/queue/sqs_helper/archiver.rb +1 -1
- data/lib/alephant/publisher/queue/sqs_helper/queue.rb +18 -10
- data/lib/alephant/publisher/queue/version.rb +1 -1
- data/lib/alephant/publisher/queue/writer.rb +20 -11
- data/lib/alephant/publisher/queue.rb +11 -3
- data/spec/archiver_spec.rb +5 -8
- data/spec/processor_spec.rb +9 -7
- data/spec/publisher_spec.rb +18 -9
- data/spec/queue_spec.rb +1 -2
- data/spec/spec_helper.rb +3 -4
- data/spec/writer_spec.rb +26 -18
- metadata +2 -2
checksums.yaml
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
---
|
2
2
|
SHA1:
|
3
|
-
metadata.gz:
|
4
|
-
data.tar.gz:
|
3
|
+
metadata.gz: 271b65caf5491b610ac599b0b66e2de1b6349006
|
4
|
+
data.tar.gz: f17b0f88a4c71649d72707b922d48e50a0fd66b5
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: d0f916092df9a3675158bd99db058cc328b5e0799e5143e4bfd7fe54ae138299c4d93d37681c7ddf900431b570417a6cb048d95288bc22c96e84331a322e90d9
|
7
|
+
data.tar.gz: 9b93abe8ba89c4c50b85b647d693cff72f3342a9c3e0d717545b9cc7708ecc6b7ec71cd38fd5f316bc7c7143e1d0ea2c2985e304b522d1c790e7721753069e94
|
data/.gitignore
CHANGED
data/Gemfile
CHANGED
@@ -1,4 +1,3 @@
|
|
1
|
-
# coding: utf-8
|
2
1
|
lib = File.expand_path("../lib", __FILE__)
|
3
2
|
$LOAD_PATH.unshift(lib) unless $LOAD_PATH.include?(lib)
|
4
3
|
require "alephant/publisher/queue/version"
|
@@ -26,7 +25,7 @@ Gem::Specification.new do |spec|
|
|
26
25
|
spec.add_development_dependency "pry"
|
27
26
|
spec.add_development_dependency "pry-remote"
|
28
27
|
spec.add_development_dependency "pry-nav"
|
29
|
-
spec.add_development_dependency
|
28
|
+
spec.add_development_dependency "rake-rspec"
|
30
29
|
|
31
30
|
spec.add_runtime_dependency "rake"
|
32
31
|
spec.add_runtime_dependency "aws-sdk", "~> 1.0"
|
@@ -50,7 +50,7 @@ module Alephant
|
|
50
50
|
begin
|
51
51
|
validate type, opts
|
52
52
|
instance.merge! opts
|
53
|
-
rescue
|
53
|
+
rescue InvalidKeySpecifiedError => e
|
54
54
|
logger.metric "QueueOptionsInvalidKeySpecified"
|
55
55
|
logger.error(
|
56
56
|
"event" => "QueueOptionsKeyInvalid",
|
@@ -64,8 +64,10 @@ module Alephant
|
|
64
64
|
end
|
65
65
|
|
66
66
|
def validate(type, opts)
|
67
|
-
opts.each do |key,
|
68
|
-
|
67
|
+
opts.each do |key, _value|
|
68
|
+
unless type.include? key.to_sym
|
69
|
+
raise InvalidKeySpecifiedError, "The key '#{key}' is invalid"
|
70
|
+
end
|
69
71
|
end
|
70
72
|
end
|
71
73
|
end
|
@@ -2,11 +2,11 @@ module Alephant
|
|
2
2
|
module Publisher
|
3
3
|
module Queue
|
4
4
|
class BaseProcessor
|
5
|
-
|
6
5
|
def consume(msg)
|
7
|
-
raise NotImplementedError.new(
|
6
|
+
raise NotImplementedError.new(
|
7
|
+
"You must implement the #consume(msg) method"
|
8
|
+
)
|
8
9
|
end
|
9
|
-
|
10
10
|
end
|
11
11
|
end
|
12
12
|
end
|
@@ -13,27 +13,35 @@ module Alephant
|
|
13
13
|
|
14
14
|
attr_reader :queue, :timeout, :wait_time, :archiver
|
15
15
|
|
16
|
-
def initialize(
|
16
|
+
def initialize(
|
17
|
+
queue,
|
18
|
+
archiver = nil,
|
19
|
+
timeout = VISABILITY_TIMEOUT,
|
20
|
+
wait_time = WAIT_TIME
|
21
|
+
)
|
17
22
|
@queue = queue
|
18
23
|
@archiver = archiver
|
19
24
|
@timeout = timeout
|
20
25
|
@wait_time = wait_time
|
26
|
+
log_queue_creation queue.url, archiver, timeout
|
27
|
+
end
|
28
|
+
|
29
|
+
def message
|
30
|
+
receive.tap { |m| process(m) unless m.nil? }
|
31
|
+
end
|
32
|
+
|
33
|
+
private
|
21
34
|
|
35
|
+
def log_queue_creation(queue_url, archiver, timeout)
|
22
36
|
logger.info(
|
23
37
|
"event" => "QueueConfigured",
|
24
|
-
"queueUrl" =>
|
38
|
+
"queueUrl" => queue_url,
|
25
39
|
"archiver" => archiver,
|
26
40
|
"timeout" => timeout,
|
27
41
|
"method" => "#{self.class}#initialize"
|
28
42
|
)
|
29
43
|
end
|
30
44
|
|
31
|
-
def message
|
32
|
-
receive.tap { |m| process(m) unless m.nil? }
|
33
|
-
end
|
34
|
-
|
35
|
-
private
|
36
|
-
|
37
45
|
def process(m)
|
38
46
|
logger.metric "MessagesReceived"
|
39
47
|
logger.info(
|
@@ -58,10 +66,10 @@ module Alephant
|
|
58
66
|
end
|
59
67
|
|
60
68
|
def receive
|
61
|
-
queue.receive_message(
|
69
|
+
queue.receive_message(
|
62
70
|
:visibility_timeout => timeout,
|
63
71
|
:wait_time_seconds => wait_time
|
64
|
-
|
72
|
+
)
|
65
73
|
end
|
66
74
|
end
|
67
75
|
end
|
@@ -41,23 +41,30 @@ module Alephant
|
|
41
41
|
protected
|
42
42
|
|
43
43
|
def perform
|
44
|
-
Proc.new
|
44
|
+
Proc.new do
|
45
|
+
views.each { |component, view| write(component, view) }
|
46
|
+
end
|
45
47
|
end
|
46
48
|
|
47
|
-
def write(
|
48
|
-
seq_for(
|
49
|
-
store(
|
49
|
+
def write(component, view)
|
50
|
+
seq_for(component).validate(message) do
|
51
|
+
store(
|
52
|
+
component,
|
53
|
+
view,
|
54
|
+
location_for(component),
|
55
|
+
:msg_id => message.id
|
56
|
+
)
|
50
57
|
end.tap do
|
51
58
|
logger.info(
|
52
59
|
"event" => "MessageWritten",
|
53
|
-
"
|
60
|
+
"component" => component,
|
54
61
|
"view" => view,
|
55
62
|
"method" => "#{self.class}#write"
|
56
63
|
)
|
57
64
|
end
|
58
65
|
end
|
59
66
|
|
60
|
-
def store(
|
67
|
+
def store(component, view, location, storage_opts = {})
|
61
68
|
render = view.render
|
62
69
|
cache.put(location, render, view.content_type, storage_opts).tap do
|
63
70
|
logger.info(
|
@@ -71,10 +78,10 @@ module Alephant
|
|
71
78
|
"method" => "#{self.class}#store"
|
72
79
|
)
|
73
80
|
end
|
74
|
-
lookup.write(
|
81
|
+
lookup.write(component, options, seq_id, location).tap do
|
75
82
|
logger.info(
|
76
83
|
"event" => "LookupLocationUpdated",
|
77
|
-
"
|
84
|
+
"component" => component,
|
78
85
|
"options" => options,
|
79
86
|
"sequenceId" => seq_id,
|
80
87
|
"location" => location,
|
@@ -83,8 +90,8 @@ module Alephant
|
|
83
90
|
end
|
84
91
|
end
|
85
92
|
|
86
|
-
def location_for(
|
87
|
-
"#{config[:renderer_id]}/#{
|
93
|
+
def location_for(component)
|
94
|
+
"#{config[:renderer_id]}/#{component}/#{opt_hash}/#{seq_id}"
|
88
95
|
end
|
89
96
|
|
90
97
|
def batch
|
@@ -109,7 +116,9 @@ module Alephant
|
|
109
116
|
end
|
110
117
|
|
111
118
|
def seq_id
|
112
|
-
@seq_id ||= Sequencer::Sequencer.sequence_id_from(
|
119
|
+
@seq_id ||= Sequencer::Sequencer.sequence_id_from(
|
120
|
+
message, config[:sequence_id_path]
|
121
|
+
)
|
113
122
|
end
|
114
123
|
|
115
124
|
def views
|
@@ -51,7 +51,7 @@ module Alephant
|
|
51
51
|
:log_archive_message => true,
|
52
52
|
:async_store => true
|
53
53
|
}
|
54
|
-
options.each do |key,
|
54
|
+
options.each do |key, _value|
|
55
55
|
options[key] = opts.queue[key] == "true" if opts.queue.has_key? key
|
56
56
|
end
|
57
57
|
end
|
@@ -68,7 +68,7 @@ module Alephant
|
|
68
68
|
end
|
69
69
|
|
70
70
|
def sqs_queue_options
|
71
|
-
(opts.queue[:aws_account_id].nil? ? {} :
|
71
|
+
(opts.queue[:aws_account_id].nil? ? {} : fallback).tap do |ops|
|
72
72
|
logger.info(
|
73
73
|
"event" => "SQSQueueOptionsConfigured",
|
74
74
|
"options" => ops,
|
@@ -77,8 +77,16 @@ module Alephant
|
|
77
77
|
end
|
78
78
|
end
|
79
79
|
|
80
|
+
def fallback
|
81
|
+
{
|
82
|
+
:queue_owner_aws_account_id => opts.queue[:aws_account_id]
|
83
|
+
}
|
84
|
+
end
|
85
|
+
|
80
86
|
def aws_queue
|
81
|
-
queue_url = sqs_client.queues.url_for(
|
87
|
+
queue_url = sqs_client.queues.url_for(
|
88
|
+
opts.queue[:sqs_queue_name], sqs_queue_options
|
89
|
+
)
|
82
90
|
sqs_client.queues[queue_url]
|
83
91
|
end
|
84
92
|
end
|
data/spec/archiver_spec.rb
CHANGED
@@ -1,4 +1,4 @@
|
|
1
|
-
require
|
1
|
+
require "spec_helper"
|
2
2
|
|
3
3
|
describe Alephant::Publisher::Queue::SQSHelper::Archiver do
|
4
4
|
let (:cache) { instance_double("Alephant::Cache", :put => nil) }
|
@@ -34,12 +34,10 @@ describe Alephant::Publisher::Queue::SQSHelper::Archiver do
|
|
34
34
|
expect(cache).to receive(:put).with(
|
35
35
|
"archive/#{time_now.strftime('%d-%m-%Y_%H')}/id",
|
36
36
|
message.body,
|
37
|
-
|
38
|
-
|
39
|
-
|
40
|
-
|
41
|
-
:queue => message.queue.url
|
42
|
-
}
|
37
|
+
:id => message.id,
|
38
|
+
:md5 => message.md5,
|
39
|
+
:logged_at => time_now.to_s,
|
40
|
+
:queue => message.queue.url
|
43
41
|
)
|
44
42
|
subject.see(message)
|
45
43
|
end
|
@@ -66,4 +64,3 @@ describe Alephant::Publisher::Queue::SQSHelper::Archiver do
|
|
66
64
|
end
|
67
65
|
end
|
68
66
|
end
|
69
|
-
|
data/spec/processor_spec.rb
CHANGED
@@ -1,19 +1,21 @@
|
|
1
|
-
require
|
1
|
+
require "spec_helper"
|
2
2
|
|
3
3
|
describe Alephant::Publisher::Queue::Processor do
|
4
|
-
|
5
4
|
before(:each) do
|
6
|
-
allow_any_instance_of(
|
7
|
-
|
5
|
+
allow_any_instance_of(
|
6
|
+
Alephant::Publisher::Queue::Writer
|
7
|
+
).to receive(:initialize)
|
8
|
+
|
9
|
+
allow_any_instance_of(
|
10
|
+
Alephant::Publisher::Queue::Writer
|
11
|
+
).to receive(:run!)
|
8
12
|
end
|
9
13
|
|
10
14
|
describe "#consume(msg)" do
|
11
15
|
it "Consume the message and deletes it" do
|
12
|
-
|
13
|
-
msg = double('AWS::SQS::ReceivedMessage', :delete => nil)
|
16
|
+
msg = double("AWS::SQS::ReceivedMessage", :delete => nil)
|
14
17
|
expect(msg).to receive(:delete)
|
15
18
|
subject.consume(msg)
|
16
|
-
|
17
19
|
end
|
18
20
|
end
|
19
21
|
end
|
data/spec/publisher_spec.rb
CHANGED
@@ -1,10 +1,12 @@
|
|
1
|
-
require
|
1
|
+
require "spec_helper"
|
2
2
|
|
3
3
|
describe Alephant::Publisher::Queue do
|
4
4
|
let(:options) { Alephant::Publisher::Queue::Options.new }
|
5
|
-
let(:queue) { double(
|
6
|
-
let(:
|
7
|
-
let(:
|
5
|
+
let(:queue) { double("AWS::SQS::Queue", :url => nil ) }
|
6
|
+
let(:client_double) { double("AWS::SQS", :queues => queue_double) }
|
7
|
+
let(:queue_double) {
|
8
|
+
double("AWS::SQS::QueueCollection", :[] => queue, :url_for => nil)
|
9
|
+
}
|
8
10
|
|
9
11
|
before(:each) do
|
10
12
|
expect(AWS::SQS).to receive(:new).and_return(client_double)
|
@@ -13,15 +15,22 @@ describe Alephant::Publisher::Queue do
|
|
13
15
|
describe ".create" do
|
14
16
|
it "sets parser, sequencer, queue and writer" do
|
15
17
|
instance = Alephant::Publisher::Queue.create(options)
|
16
|
-
expect(instance.queue)
|
18
|
+
expect(instance.queue)
|
19
|
+
.to be_a Alephant::Publisher::Queue::SQSHelper::Queue
|
17
20
|
end
|
18
21
|
|
19
22
|
context "with account" do
|
20
23
|
it "creates a queue with an account number in the option hash" do
|
21
24
|
options = Alephant::Publisher::Queue::Options.new
|
22
|
-
options.add_queue(
|
25
|
+
options.add_queue(
|
26
|
+
:sqs_queue_name => "bar",
|
27
|
+
:aws_account_id => "foo"
|
28
|
+
)
|
23
29
|
|
24
|
-
expect(queue_double).to receive(:url_for).with(
|
30
|
+
expect(queue_double).to receive(:url_for).with(
|
31
|
+
"bar",
|
32
|
+
:queue_owner_aws_account_id => "foo"
|
33
|
+
)
|
25
34
|
|
26
35
|
Alephant::Publisher::Queue.create(options)
|
27
36
|
end
|
@@ -30,9 +39,9 @@ describe Alephant::Publisher::Queue do
|
|
30
39
|
context "without account" do
|
31
40
|
it "creates a queue with an empty option hash" do
|
32
41
|
options = Alephant::Publisher::Queue::Options.new
|
33
|
-
options.add_queue(
|
42
|
+
options.add_queue(:sqs_queue_name => "bar")
|
34
43
|
|
35
|
-
expect(queue_double).to receive(:url_for).with(
|
44
|
+
expect(queue_double).to receive(:url_for).with("bar", {})
|
36
45
|
|
37
46
|
Alephant::Publisher::Queue.create(options)
|
38
47
|
end
|
data/spec/queue_spec.rb
CHANGED
data/spec/spec_helper.rb
CHANGED
data/spec/writer_spec.rb
CHANGED
@@ -1,14 +1,14 @@
|
|
1
|
-
require
|
1
|
+
require "spec_helper"
|
2
2
|
|
3
3
|
describe Alephant::Publisher::Queue::Writer do
|
4
4
|
let(:opts) do
|
5
5
|
{
|
6
|
-
:lookup_table_name =>
|
7
|
-
:msg_vary_id_path =>
|
6
|
+
:lookup_table_name => "lookup_table_name",
|
7
|
+
:msg_vary_id_path => "$.vary",
|
8
8
|
:renderer_id => :renderer_id,
|
9
9
|
:s3_bucket_id => :s3_bucket_id,
|
10
10
|
:s3_object_path => :s3_object_path,
|
11
|
-
:sequence_id_path =>
|
11
|
+
:sequence_id_path => "$.sequence",
|
12
12
|
:sequencer_table_name => :sequencer_table_name,
|
13
13
|
:view_path => :view_path
|
14
14
|
}
|
@@ -23,37 +23,45 @@ describe Alephant::Publisher::Queue::Writer do
|
|
23
23
|
opts[:s3_object_path]
|
24
24
|
)
|
25
25
|
|
26
|
-
allow_any_instance_of(Alephant::Sequencer::SequenceTable).to receive(:create)
|
27
26
|
|
28
|
-
allow_any_instance_of(
|
29
|
-
|
27
|
+
allow_any_instance_of(
|
28
|
+
Alephant::Sequencer::SequenceTable
|
29
|
+
).to receive(:create)
|
30
30
|
|
31
|
-
allow_any_instance_of(Alephant::Sequencer::Sequencer).to receive(:set_last_seen)
|
32
31
|
|
33
|
-
allow_any_instance_of(Alephant::Sequencer::Sequencer)
|
34
|
-
|
35
|
-
|
32
|
+
allow_any_instance_of(Alephant::Sequencer::Sequencer)
|
33
|
+
.to receive_messages(
|
34
|
+
:sequencer_id_from => nil,
|
35
|
+
:set_last_seen => nil,
|
36
|
+
:get_last_seen => nil
|
37
|
+
)
|
36
38
|
|
37
|
-
allow_any_instance_of(Alephant::Lookup::LookupTable)
|
39
|
+
allow_any_instance_of(Alephant::Lookup::LookupTable)
|
40
|
+
.to receive_messages(
|
41
|
+
:create => nil,
|
42
|
+
:table_name => nil
|
43
|
+
)
|
38
44
|
|
39
|
-
allow_any_instance_of(
|
45
|
+
allow_any_instance_of(
|
46
|
+
Alephant::Renderer::Renderer
|
47
|
+
).to receive(:views).and_return({})
|
40
48
|
end
|
41
49
|
|
42
50
|
describe "#run!" do
|
43
51
|
let(:msg) do
|
44
52
|
data = {
|
45
53
|
"sequence" => "1",
|
46
|
-
"vary"
|
54
|
+
"vary" => "foo"
|
47
55
|
}
|
48
|
-
Struct.new(:body
|
56
|
+
Struct.new(:body, :id).new(data.to_json, "id")
|
49
57
|
end
|
50
58
|
|
51
59
|
let(:expected_location) do
|
52
|
-
|
60
|
+
"renderer_id/component_id/218c835cec343537589dbf1619532e4d/1"
|
53
61
|
end
|
54
62
|
|
55
63
|
let(:renderer) do
|
56
|
-
instance_double
|
64
|
+
instance_double "Alephant::Renderer::Renderer"
|
57
65
|
end
|
58
66
|
|
59
67
|
subject do
|
@@ -66,7 +74,7 @@ describe Alephant::Publisher::Queue::Writer do
|
|
66
74
|
allow_any_instance_of(Alephant::Lookup::LookupHelper).to receive(:write)
|
67
75
|
.with(
|
68
76
|
"component_id",
|
69
|
-
{:variant=>"foo"},
|
77
|
+
{ :variant => "foo" },
|
70
78
|
1,
|
71
79
|
expected_location
|
72
80
|
)
|
metadata
CHANGED
@@ -1,14 +1,14 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: alephant-publisher-queue
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 2.0.
|
4
|
+
version: 2.0.1
|
5
5
|
platform: ruby
|
6
6
|
authors:
|
7
7
|
- BBC News
|
8
8
|
autorequire:
|
9
9
|
bindir: bin
|
10
10
|
cert_chain: []
|
11
|
-
date: 2015-
|
11
|
+
date: 2015-12-03 00:00:00.000000000 Z
|
12
12
|
dependencies:
|
13
13
|
- !ruby/object:Gem::Dependency
|
14
14
|
requirement: !ruby/object:Gem::Requirement
|