propono 0.8.2 → 0.9.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.
- checksums.yaml +4 -4
- data/CHANGELOG.md +4 -0
- data/README.md +1 -0
- data/Rakefile +1 -1
- data/lib/propono.rb +6 -5
- data/lib/propono/helpers/hash.rb +10 -0
- data/lib/propono/services/publisher.rb +19 -9
- data/lib/propono/services/queue_listener.rb +14 -2
- data/lib/propono/services/tcp_listener.rb +10 -2
- data/lib/propono/services/udp_listener.rb +10 -2
- data/lib/propono/version.rb +1 -1
- data/test/helpers/hash_test.rb +30 -0
- data/test/integration/sns_to_sqs_test.rb +13 -4
- data/test/integration/tcp_to_sqs_test.rb +12 -3
- data/test/integration/udp_proxy_test.rb +15 -5
- data/test/integration/udp_to_sqs_test.rb +12 -3
- data/test/propono_test.rb +6 -4
- data/test/services/publisher_test.rb +44 -21
- data/test/services/queue_listener_test.rb +64 -6
- data/test/services/tcp_listener_test.rb +16 -3
- data/test/services/udp_listener_test.rb +16 -2
- data/test/test_helper.rb +1 -0
- metadata +6 -3
checksums.yaml
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
---
|
2
2
|
SHA1:
|
3
|
-
metadata.gz:
|
4
|
-
data.tar.gz:
|
3
|
+
metadata.gz: b1a85c42b5fc2bc691203ab82f348535476bdf35
|
4
|
+
data.tar.gz: af8fc9263c84a713779bee0e019258220102549f
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: b80edaee162402a479bff3a14cf05b56fd3e37bd5838faf7fbc040194028aa7451e12bf6b9bf551ca25fa1903a104a68083c5514b6afd6e9e137e955bcedeeb4
|
7
|
+
data.tar.gz: 994bdbb18b1cde05e45415d90ef435545a5e5647c1d8d466eee912e2b62a318677c1a0af658b1a718caee78fbcb6ffa1b46ac64707922cbc3c37f017d4ab811c
|
data/CHANGELOG.md
CHANGED
data/README.md
CHANGED
data/Rakefile
CHANGED
data/lib/propono.rb
CHANGED
@@ -1,12 +1,13 @@
|
|
1
1
|
# Propono
|
2
2
|
#
|
3
3
|
# Propono is a pub/sub gem built on top of Amazon Web Services (AWS). It uses Simple Notification Service (SNS) and Simple Queue Service (SQS) to seamlessly pass messages throughout your infrastructure.
|
4
|
-
|
5
4
|
require "propono/version"
|
6
5
|
require 'propono/propono_error'
|
7
6
|
require 'propono/logger'
|
8
7
|
require 'propono/configuration'
|
9
8
|
|
9
|
+
require "propono/helpers/hash"
|
10
|
+
|
10
11
|
require 'propono/components/sns'
|
11
12
|
require 'propono/components/sqs'
|
12
13
|
require "propono/components/queue"
|
@@ -130,8 +131,8 @@ module Propono
|
|
130
131
|
# This method uses #listen_to_udp and #publish to proxy
|
131
132
|
# messages from UDP onto the queue.
|
132
133
|
def self.proxy_udp
|
133
|
-
Propono.listen_to_udp do |topic, message|
|
134
|
-
Propono.publish(topic, message)
|
134
|
+
Propono.listen_to_udp do |topic, message, options = {}|
|
135
|
+
Propono.publish(topic, message, options)
|
135
136
|
end
|
136
137
|
end
|
137
138
|
|
@@ -140,8 +141,8 @@ module Propono
|
|
140
141
|
# This method uses #listen_to_tcp and #publish to proxy
|
141
142
|
# messages from TCP onto the queue.
|
142
143
|
def self.proxy_tcp
|
143
|
-
Propono.listen_to_tcp do |topic, message|
|
144
|
-
Propono.publish(topic, message)
|
144
|
+
Propono.listen_to_tcp do |topic, message, options = {}|
|
145
|
+
Propono.publish(topic, message, options)
|
145
146
|
end
|
146
147
|
end
|
147
148
|
end
|
@@ -11,19 +11,23 @@ module Propono
|
|
11
11
|
new(topic_id, message, options).publish
|
12
12
|
end
|
13
13
|
|
14
|
-
attr_reader :topic_id, :message, :protocol
|
14
|
+
attr_reader :topic_id, :message, :protocol, :id
|
15
15
|
|
16
16
|
def initialize(topic_id, message, options = {})
|
17
17
|
raise PublisherError.new("Topic is nil") if topic_id.nil?
|
18
18
|
raise PublisherError.new("Message is nil") if message.nil?
|
19
19
|
|
20
|
+
options = options.symbolize_keys
|
21
|
+
|
20
22
|
@topic_id = topic_id
|
21
23
|
@message = message
|
22
24
|
@protocol = options.fetch(:protocol, :sns).to_sym
|
25
|
+
@id = SecureRandom.hex(3)
|
26
|
+
@id = "#{options[:id]}-#{@id}" if options[:id]
|
23
27
|
end
|
24
28
|
|
25
29
|
def publish
|
26
|
-
Propono.config.logger.info "Propono: Publishing #{message} to #{topic_id} via #{protocol}"
|
30
|
+
Propono.config.logger.info "Propono [#{id}]: Publishing #{message} to #{topic_id} via #{protocol}"
|
27
31
|
send("publish_via_#{protocol}")
|
28
32
|
end
|
29
33
|
|
@@ -31,31 +35,37 @@ module Propono
|
|
31
35
|
|
32
36
|
def publish_via_sns
|
33
37
|
topic = TopicCreator.find_or_create(topic_id)
|
34
|
-
msg = message.is_a?(String) ? message : message.to_json
|
35
38
|
Thread.new do
|
36
39
|
begin
|
37
|
-
sns.publish(topic.arn,
|
40
|
+
sns.publish(topic.arn, body.to_json)
|
38
41
|
rescue => e
|
39
|
-
Propono.config.logger.error "Propono
|
42
|
+
Propono.config.logger.error "Propono [#{id}]: Failed to send via sns : #{e}"
|
40
43
|
end
|
41
44
|
end
|
42
45
|
end
|
43
46
|
|
44
47
|
def publish_via_udp
|
45
|
-
payload =
|
48
|
+
payload = body.merge(topic: topic_id).to_json
|
46
49
|
UDPSocket.new.send(payload, 0, Propono.config.udp_host, Propono.config.udp_port)
|
47
50
|
rescue => e
|
48
|
-
Propono.config.logger.error "Propono
|
51
|
+
Propono.config.logger.error "Propono [#{id}]: Failed to send : #{e}"
|
49
52
|
end
|
50
53
|
|
51
54
|
def publish_via_tcp
|
52
|
-
payload =
|
55
|
+
payload = body.merge(topic: topic_id).to_json
|
53
56
|
|
54
57
|
socket = TCPSocket.new(Propono.config.tcp_host, Propono.config.tcp_port)
|
55
58
|
socket.write payload
|
56
59
|
socket.close
|
57
60
|
rescue => e
|
58
|
-
Propono.config.logger.error "Propono
|
61
|
+
Propono.config.logger.error "Propono [#{id}]: Failed to send : #{e}"
|
62
|
+
end
|
63
|
+
|
64
|
+
def body
|
65
|
+
{
|
66
|
+
id: id,
|
67
|
+
message: message
|
68
|
+
}
|
59
69
|
end
|
60
70
|
end
|
61
71
|
end
|
@@ -36,8 +36,20 @@ module Propono
|
|
36
36
|
end
|
37
37
|
|
38
38
|
def process_sqs_message(sqs_message)
|
39
|
-
|
40
|
-
|
39
|
+
body = JSON.parse(sqs_message["Body"])["Message"]
|
40
|
+
|
41
|
+
# Legacy syntax is covered in the rescue statement
|
42
|
+
# This begin/rescue dance and the rescue block will be removed in v1.
|
43
|
+
begin
|
44
|
+
body = JSON.parse(body)
|
45
|
+
context = body.symbolize_keys
|
46
|
+
message = context.delete(:message)
|
47
|
+
Propono.config.logger.info "Propono [#{context[:id]}]: Received from sqs."
|
48
|
+
@message_processor.call(message, context)
|
49
|
+
rescue
|
50
|
+
Propono.config.logger.info("Sending and recieving messags without ids is deprecated")
|
51
|
+
@message_processor.call(body)
|
52
|
+
end
|
41
53
|
sqs.delete_message(queue_url, sqs_message['ReceiptHandle'])
|
42
54
|
end
|
43
55
|
|
@@ -29,8 +29,16 @@ module Propono
|
|
29
29
|
end
|
30
30
|
|
31
31
|
def process_tcp_data(tcp_data)
|
32
|
-
json = JSON.parse(tcp_data)
|
33
|
-
|
32
|
+
json = JSON.parse(tcp_data).symbolize_keys
|
33
|
+
|
34
|
+
# Legacy syntax is covered in the else statement
|
35
|
+
# This conditional and the else block will be removed in v1.
|
36
|
+
if json[:id]
|
37
|
+
@processor.call(json[:topic], json[:message], id: json[:id])
|
38
|
+
else
|
39
|
+
Propono.config.logger.info("Sending and recieving messags without ids is deprecated")
|
40
|
+
@processor.call(json[:topic], json[:message])
|
41
|
+
end
|
34
42
|
end
|
35
43
|
|
36
44
|
def server
|
@@ -27,8 +27,16 @@ module Propono
|
|
27
27
|
end
|
28
28
|
|
29
29
|
def process_udp_data(udp_data)
|
30
|
-
json = JSON.parse(udp_data)
|
31
|
-
|
30
|
+
json = JSON.parse(udp_data).symbolize_keys
|
31
|
+
|
32
|
+
# Legacy syntax is covered in the else statement
|
33
|
+
# This conditional and the else block will be removed in v1.
|
34
|
+
if json[:id]
|
35
|
+
@processor.call(json[:topic], json[:message], id: json[:id])
|
36
|
+
else
|
37
|
+
Propono.config.logger.info("Sending and recieving messags without ids is deprecated")
|
38
|
+
@processor.call(json[:topic], json[:message])
|
39
|
+
end
|
32
40
|
end
|
33
41
|
|
34
42
|
def socket
|
data/lib/propono/version.rb
CHANGED
@@ -0,0 +1,30 @@
|
|
1
|
+
require File.expand_path('../../test_helper', __FILE__)
|
2
|
+
|
3
|
+
module Propono
|
4
|
+
class HashTest < Minitest::Test
|
5
|
+
def test_symbolize_keys_works
|
6
|
+
input = {
|
7
|
+
"foo" => "bar",
|
8
|
+
cat: 1,
|
9
|
+
"nest" => {
|
10
|
+
"dog" => [
|
11
|
+
{"mouse" => true}
|
12
|
+
]
|
13
|
+
}
|
14
|
+
}
|
15
|
+
expected = {
|
16
|
+
foo: 'bar',
|
17
|
+
cat: 1,
|
18
|
+
nest: {
|
19
|
+
dog: [
|
20
|
+
{"mouse" => true}
|
21
|
+
]
|
22
|
+
}
|
23
|
+
}
|
24
|
+
|
25
|
+
assert_equal expected, input.symbolize_keys
|
26
|
+
end
|
27
|
+
end
|
28
|
+
end
|
29
|
+
|
30
|
+
|
@@ -5,20 +5,29 @@ module Propono
|
|
5
5
|
def test_the_message_gets_there
|
6
6
|
topic = "test-topic"
|
7
7
|
text = "This is my message"
|
8
|
+
flunks = []
|
8
9
|
|
9
10
|
Propono.subscribe_by_queue(topic)
|
10
11
|
|
11
12
|
thread = Thread.new do
|
12
|
-
|
13
|
-
|
14
|
-
|
13
|
+
begin
|
14
|
+
Propono.listen_to_queue(topic) do |message, context|
|
15
|
+
flunks << "Wrong message" unless message == text
|
16
|
+
flunks << "Wrong id" unless context[:id] =~ Regexp.new("[a-z0-9]{6}")
|
17
|
+
break
|
18
|
+
end
|
19
|
+
rescue => e
|
20
|
+
flunks << e.message
|
21
|
+
ensure
|
22
|
+
thread.terminate
|
15
23
|
end
|
16
24
|
end
|
17
25
|
|
18
26
|
sleep(2) # Make sure the listener has started
|
19
27
|
|
20
28
|
Propono.publish(topic, text)
|
21
|
-
|
29
|
+
flunks << "Test Timeout" unless wait_for_thread(thread)
|
30
|
+
flunk(flunks.join("\n")) unless flunks.empty?
|
22
31
|
ensure
|
23
32
|
thread.terminate
|
24
33
|
end
|
@@ -5,14 +5,22 @@ module Propono
|
|
5
5
|
def test_the_message_gets_there
|
6
6
|
topic = "test-topic"
|
7
7
|
message = "This is my message"
|
8
|
+
flunks = []
|
9
|
+
|
8
10
|
Propono.config.tcp_host = "localhost"
|
9
11
|
Propono.config.tcp_port = 20009
|
10
12
|
|
11
13
|
Propono.subscribe_by_queue(topic)
|
12
14
|
|
13
15
|
sqs_thread = Thread.new do
|
14
|
-
|
15
|
-
|
16
|
+
begin
|
17
|
+
Propono.listen_to_queue(topic) do |sqs_message|
|
18
|
+
flunks << "Wrong message" unless message == sqs_message
|
19
|
+
sqs_thread.terminate
|
20
|
+
end
|
21
|
+
rescue => e
|
22
|
+
flunks << e.message
|
23
|
+
ensure
|
16
24
|
sqs_thread.terminate
|
17
25
|
end
|
18
26
|
end
|
@@ -26,7 +34,8 @@ module Propono
|
|
26
34
|
sleep(2) # Make sure the listener has started
|
27
35
|
|
28
36
|
Propono.publish(topic, message, protocol: :tcp)
|
29
|
-
|
37
|
+
flunks << "Test Timeout" unless wait_for_thread(tcp_thread) && wait_for_thread(sqs_thread)
|
38
|
+
flunk(flunks.join("\n")) unless flunks.empty?
|
30
39
|
ensure
|
31
40
|
tcp_thread.terminate
|
32
41
|
sqs_thread.terminate
|
@@ -4,14 +4,23 @@ module Propono
|
|
4
4
|
class UdpProxyTest < IntegrationTest
|
5
5
|
def test_the_message_gets_there
|
6
6
|
topic = "test-topic"
|
7
|
-
|
7
|
+
text = "This is my message"
|
8
|
+
flunks = []
|
9
|
+
|
8
10
|
Propono.config.udp_port = 20001
|
9
11
|
|
10
12
|
Propono.subscribe_by_queue(topic)
|
11
13
|
|
12
14
|
sqs_thread = Thread.new do
|
13
|
-
|
14
|
-
|
15
|
+
begin
|
16
|
+
Propono.listen_to_queue(topic) do |message, context|
|
17
|
+
flunks << "Wrong message" unless text == message
|
18
|
+
flunks << "Wrong id" unless context[:id] =~ Regexp.new("[a-z0-9]{6}-[a-z0-9]{6}")
|
19
|
+
break
|
20
|
+
end
|
21
|
+
rescue => e
|
22
|
+
flunks << e.message
|
23
|
+
ensure
|
15
24
|
sqs_thread.terminate
|
16
25
|
end
|
17
26
|
end
|
@@ -22,8 +31,9 @@ module Propono
|
|
22
31
|
|
23
32
|
sleep(2) # Make sure the proxy has started
|
24
33
|
|
25
|
-
Propono.publish(topic,
|
26
|
-
|
34
|
+
Propono::Publisher.publish(topic, text, protocol: :udp)
|
35
|
+
flunks << "Test timeout" unless wait_for_thread(sqs_thread)
|
36
|
+
flunk(flunks.join("\n")) unless flunks.empty?
|
27
37
|
ensure
|
28
38
|
udp_thread.terminate
|
29
39
|
sqs_thread.terminate
|
@@ -5,13 +5,21 @@ module Propono
|
|
5
5
|
def test_the_message_gets_there
|
6
6
|
topic = "test-topic"
|
7
7
|
message = "This is my message"
|
8
|
+
flunks = []
|
9
|
+
|
8
10
|
Propono.config.udp_port = 20002
|
9
11
|
|
10
12
|
Propono.subscribe_by_queue(topic)
|
11
13
|
|
12
14
|
sqs_thread = Thread.new do
|
13
|
-
|
14
|
-
|
15
|
+
begin
|
16
|
+
Propono.listen_to_queue(topic) do |sqs_message|
|
17
|
+
assert_equal message, sqs_message
|
18
|
+
sqs_thread.terminate
|
19
|
+
end
|
20
|
+
rescue => e
|
21
|
+
flunks << e.message
|
22
|
+
ensure
|
15
23
|
sqs_thread.terminate
|
16
24
|
end
|
17
25
|
end
|
@@ -26,7 +34,8 @@ module Propono
|
|
26
34
|
sleep(2) # Make sure the listener has started
|
27
35
|
|
28
36
|
Propono.publish(topic, message, protocol: :udp)
|
29
|
-
|
37
|
+
flunks << "Test Timeout" unless wait_for_thread(udp_thread) && wait_for_thread(sqs_thread)
|
38
|
+
flunk(flunks.join("\n")) unless flunks.empty?
|
30
39
|
ensure
|
31
40
|
udp_thread.terminate
|
32
41
|
sqs_thread.terminate
|
data/test/propono_test.rb
CHANGED
@@ -45,8 +45,9 @@ module Propono
|
|
45
45
|
def test_proxy_udp_calls_publish_in_the_block
|
46
46
|
topic = "foobar"
|
47
47
|
message = "message"
|
48
|
-
|
49
|
-
|
48
|
+
options = {id: "catdog"}
|
49
|
+
Propono.stubs(:listen_to_udp).yields(topic, message, options)
|
50
|
+
Publisher.expects(:publish).with(topic, message, options)
|
50
51
|
Propono.proxy_udp
|
51
52
|
end
|
52
53
|
|
@@ -58,8 +59,9 @@ module Propono
|
|
58
59
|
def test_proxy_tcp_calls_publish_in_the_block
|
59
60
|
topic = "foobar"
|
60
61
|
message = "message"
|
61
|
-
|
62
|
-
|
62
|
+
options = {id: "catdog"}
|
63
|
+
Propono.stubs(:listen_to_tcp).yields(topic, message, options)
|
64
|
+
Publisher.expects(:publish).with(topic, message, options)
|
63
65
|
Propono.proxy_tcp
|
64
66
|
end
|
65
67
|
end
|
@@ -15,6 +15,17 @@ module Propono
|
|
15
15
|
Publisher.publish(topic, message)
|
16
16
|
end
|
17
17
|
|
18
|
+
def test_initializer_generates_an_id
|
19
|
+
publisher = Publisher.new('x','y')
|
20
|
+
assert publisher.instance_variable_get(:@id)
|
21
|
+
end
|
22
|
+
|
23
|
+
def test_initializer_concats_an_id
|
24
|
+
id = "q1w2e3"
|
25
|
+
publisher = Publisher.new('x','y', id: id)
|
26
|
+
assert publisher.id =~ Regexp.new("^#{id}-[a-z0-9]{6}$")
|
27
|
+
end
|
28
|
+
|
18
29
|
def test_self_publish_calls_publish
|
19
30
|
Publisher.any_instance.expects(:publish)
|
20
31
|
Publisher.publish("topic", "message")
|
@@ -26,9 +37,10 @@ module Propono
|
|
26
37
|
end
|
27
38
|
|
28
39
|
def test_publish_logs
|
29
|
-
|
30
|
-
|
31
|
-
|
40
|
+
publisher = Publisher.new("foo", "bar")
|
41
|
+
publisher.instance_variable_set(:@id, 'abc')
|
42
|
+
Propono.config.logger.expects(:info).with() {|x| x =~ /^Propono \[abc\]: Publishing bar to foo via sns.*/}
|
43
|
+
publisher.send(:publish)
|
32
44
|
end
|
33
45
|
|
34
46
|
def test_publish_proxies_to_sns
|
@@ -45,6 +57,7 @@ module Propono
|
|
45
57
|
|
46
58
|
def test_publish_via_sns_should_call_sns_on_correct_topic_and_message
|
47
59
|
topic = "topic123"
|
60
|
+
id = "f123"
|
48
61
|
message = "message123"
|
49
62
|
topic_arn = "arn123"
|
50
63
|
topic = Topic.new(topic_arn)
|
@@ -52,41 +65,45 @@ module Propono
|
|
52
65
|
TopicCreator.stubs(find_or_create: topic)
|
53
66
|
|
54
67
|
sns = mock()
|
55
|
-
sns.expects(:publish).with(topic_arn, message)
|
68
|
+
sns.expects(:publish).with(topic_arn, {id: id, message: message}.to_json)
|
56
69
|
publisher = Publisher.new(topic, message)
|
57
|
-
publisher.stubs(sns: sns)
|
70
|
+
publisher.stubs(id: id, sns: sns)
|
58
71
|
thread = publisher.send(:publish_via_sns)
|
59
72
|
thread.join
|
60
73
|
end
|
61
74
|
|
62
75
|
def test_publish_via_sns_should_accept_a_hash_for_message
|
63
76
|
topic = "topic123"
|
77
|
+
id = "foobar123"
|
64
78
|
message = {something: ['some', 123, true]}
|
79
|
+
body = {id: id, message: message}
|
80
|
+
|
65
81
|
topic_arn = "arn123"
|
66
82
|
topic = Topic.new(topic_arn)
|
67
|
-
|
68
83
|
TopicCreator.stubs(find_or_create: topic)
|
69
84
|
|
70
85
|
sns = mock()
|
71
|
-
sns.expects(:publish).with(topic_arn,
|
86
|
+
sns.expects(:publish).with(topic_arn, body.to_json)
|
72
87
|
publisher = Publisher.new(topic, message)
|
73
|
-
publisher.stubs(sns: sns)
|
88
|
+
publisher.stubs(id: id, sns: sns)
|
74
89
|
thread = publisher.send(:publish_via_sns)
|
75
90
|
thread.join
|
76
91
|
end
|
77
92
|
|
78
93
|
def test_publish_via_sns_should_return_future_of_the_sns_response
|
79
94
|
topic = "topic123"
|
95
|
+
id = "foobar123"
|
80
96
|
message = "message123"
|
97
|
+
body = {id: id, message: message}
|
98
|
+
|
81
99
|
topic_arn = "arn123"
|
82
100
|
topic = Topic.new(topic_arn)
|
83
|
-
|
84
101
|
TopicCreator.stubs(find_or_create: topic)
|
85
102
|
|
86
103
|
sns = mock()
|
87
|
-
sns.expects(:publish).with(topic_arn,
|
104
|
+
sns.expects(:publish).with(topic_arn, body.to_json).returns(:response)
|
88
105
|
publisher = Publisher.new(topic, message)
|
89
|
-
publisher.stubs(sns: sns)
|
106
|
+
publisher.stubs(id: id, sns: sns)
|
90
107
|
assert_same :response, publisher.send(:publish_via_sns).value
|
91
108
|
end
|
92
109
|
|
@@ -109,7 +126,6 @@ module Propono
|
|
109
126
|
sns = mock()
|
110
127
|
sns.stubs(:publish)
|
111
128
|
publisher = Publisher.new(topic_id, "Foobar")
|
112
|
-
publisher.stubs(sns: sns)
|
113
129
|
|
114
130
|
publisher.send(:publish_via_sns)
|
115
131
|
end
|
@@ -120,11 +136,14 @@ module Propono
|
|
120
136
|
Propono.config.udp_host = host
|
121
137
|
Propono.config.udp_port = port
|
122
138
|
topic_id = "my-fav-topic"
|
123
|
-
|
124
|
-
|
139
|
+
|
140
|
+
id = "foobar123"
|
141
|
+
message = "cat dog mouse"
|
142
|
+
payload = {id: id, message: message, topic: topic_id}.to_json
|
125
143
|
UDPSocket.any_instance.expects(:send).with(payload, 0, host, port)
|
126
144
|
|
127
145
|
publisher = Publisher.new(topic_id, message)
|
146
|
+
publisher.stubs(id: id)
|
128
147
|
publisher.send(:publish_via_udp)
|
129
148
|
end
|
130
149
|
|
@@ -134,9 +153,10 @@ module Propono
|
|
134
153
|
Propono.config.udp_host = host
|
135
154
|
Propono.config.udp_port = port
|
136
155
|
|
137
|
-
|
138
|
-
|
139
|
-
|
156
|
+
publisher = Publisher.new("topic_id", "message")
|
157
|
+
publisher.stubs(id: '123asd')
|
158
|
+
Propono.config.logger.expects(:error).with() {|x| x =~ /^Propono \[123asd\]: Failed to send : getaddrinfo:.*/}
|
159
|
+
publisher.send(:publish_via_udp)
|
140
160
|
end
|
141
161
|
|
142
162
|
def test_publish_should_raise_exception_if_topic_is_nil
|
@@ -149,8 +169,9 @@ module Propono
|
|
149
169
|
Propono.config.tcp_host = "http://meducation.net"
|
150
170
|
Propono.config.tcp_port = 1234
|
151
171
|
topic_id = "my-fav-topic"
|
172
|
+
id = "qweqw2312"
|
152
173
|
message = "foobar"
|
153
|
-
payload = {
|
174
|
+
payload = {id: id, message: message, topic: topic_id}.to_json
|
154
175
|
|
155
176
|
socket = mock()
|
156
177
|
socket.expects(:write).with(payload)
|
@@ -158,6 +179,7 @@ module Propono
|
|
158
179
|
TCPSocket.stubs(new: socket)
|
159
180
|
|
160
181
|
publisher = Publisher.new(topic_id, message)
|
182
|
+
publisher.stubs(id: id)
|
161
183
|
publisher.send(:publish_via_tcp)
|
162
184
|
end
|
163
185
|
|
@@ -180,9 +202,10 @@ module Propono
|
|
180
202
|
Propono.config.tcp_host = host
|
181
203
|
Propono.config.tcp_port = port
|
182
204
|
|
183
|
-
|
184
|
-
|
185
|
-
|
205
|
+
publisher = Publisher.new("topic_id", "message")
|
206
|
+
publisher.stubs(id: '123asd')
|
207
|
+
Propono.config.logger.expects(:error).with() {|x| x =~ /^Propono \[123asd\]: Failed to send : getaddrinfo:.*/}
|
208
|
+
publisher.send(:publish_via_tcp)
|
186
209
|
end
|
187
210
|
|
188
211
|
def test_publish_should_raise_exception_if_topic_is_nil
|
@@ -9,10 +9,14 @@ module Propono
|
|
9
9
|
|
10
10
|
@receipt_handle1 = "test-receipt-handle1"
|
11
11
|
@receipt_handle2 = "test-receipt-handle2"
|
12
|
-
@message1 = "Foobar 123"
|
12
|
+
@message1 = {cat: "Foobar 123"}
|
13
13
|
@message2 = "Barfoo 543"
|
14
|
-
@
|
15
|
-
@
|
14
|
+
@message1_id = "abc123"
|
15
|
+
@message1_id = "987whf"
|
16
|
+
@body1 = {id: @message1_id, message: @message1}
|
17
|
+
@body2 = {id: @message2_id, message: @message2}
|
18
|
+
@sqs_message1 = { "ReceiptHandle" => @receipt_handle1, "Body" => {"Message" => @body1.to_json}.to_json}
|
19
|
+
@sqs_message2 = { "ReceiptHandle" => @receipt_handle2, "Body" => {"Message" => @body2.to_json}.to_json}
|
16
20
|
@messages = { "Message" => [ @sqs_message1, @sqs_message2 ] }
|
17
21
|
@sqs_response = mock().tap{|m|m.stubs(body: @messages)}
|
18
22
|
@sqs = mock()
|
@@ -40,6 +44,11 @@ module Propono
|
|
40
44
|
@listener.send(:read_messages)
|
41
45
|
end
|
42
46
|
|
47
|
+
def test_log_message_from_sqs
|
48
|
+
Propono.config.logger.expects(:info).with() {|x| x == "Propono [#{@message1_id}]: Received from sqs."}
|
49
|
+
@listener.send(:read_messages)
|
50
|
+
end
|
51
|
+
|
43
52
|
def test_read_messages_calls_process_message_for_each_msg
|
44
53
|
@listener.expects(:process_sqs_message).with(@sqs_message1)
|
45
54
|
@listener.expects(:process_sqs_message).with(@sqs_message2)
|
@@ -66,10 +75,9 @@ module Propono
|
|
66
75
|
end
|
67
76
|
|
68
77
|
def test_each_message_processor_is_yielded
|
69
|
-
messages_yielded = [
|
70
|
-
@listener = QueueListener.new(@topic_id) { |m| messages_yielded.push(m) }
|
78
|
+
messages_yielded = []
|
79
|
+
@listener = QueueListener.new(@topic_id) { |m, _| messages_yielded.push(m) }
|
71
80
|
@listener.stubs(sqs: @sqs)
|
72
|
-
|
73
81
|
@listener.send(:read_messages)
|
74
82
|
|
75
83
|
assert_equal messages_yielded.size, 2
|
@@ -77,6 +85,17 @@ module Propono
|
|
77
85
|
assert messages_yielded.include?(@message2)
|
78
86
|
end
|
79
87
|
|
88
|
+
def test_each_message_processor_context
|
89
|
+
contexts = []
|
90
|
+
@listener = QueueListener.new(@topic_id) { |_, context| contexts << context }
|
91
|
+
@listener.stubs(sqs: @sqs)
|
92
|
+
@listener.send(:read_messages)
|
93
|
+
|
94
|
+
assert_equal contexts.size, 2
|
95
|
+
assert contexts.include?({id: @message1_id})
|
96
|
+
assert contexts.include?({id: @message2_id})
|
97
|
+
end
|
98
|
+
|
80
99
|
def test_each_message_is_deleted
|
81
100
|
queue_url = "test-queue-url"
|
82
101
|
|
@@ -87,4 +106,43 @@ module Propono
|
|
87
106
|
@listener.send(:read_messages)
|
88
107
|
end
|
89
108
|
end
|
109
|
+
class QueueListenerLegacySyntaxTest < Minitest::Test
|
110
|
+
|
111
|
+
def setup
|
112
|
+
super
|
113
|
+
@topic_id = "some-topic"
|
114
|
+
|
115
|
+
@receipt_handle1 = "test-receipt-handle1"
|
116
|
+
@receipt_handle2 = "test-receipt-handle2"
|
117
|
+
@message1 = {'cat' => "Foobar 123"}
|
118
|
+
@message2 = "qwertyuiop"
|
119
|
+
@sqs_message1 = { "ReceiptHandle" => @receipt_handle1, "Body" => {"Message" => @message1}.to_json}
|
120
|
+
@sqs_message2 = { "ReceiptHandle" => @receipt_handle2, "Body" => {"Message" => @message2}.to_json}
|
121
|
+
@messages = { "Message" => [ @sqs_message1, @sqs_message2 ] }
|
122
|
+
@sqs_response = mock().tap{|m|m.stubs(body: @messages)}
|
123
|
+
@sqs = mock()
|
124
|
+
@sqs.stubs(receive_message: @sqs_response)
|
125
|
+
@sqs.stubs(:delete_message)
|
126
|
+
|
127
|
+
@listener = QueueListener.new(@topic_id) {}
|
128
|
+
@listener.stubs(sqs: @sqs)
|
129
|
+
end
|
130
|
+
|
131
|
+
def test_old_syntax_has_deprecation_warning
|
132
|
+
Propono.config.logger.expects(:info).with("Sending and recieving messags without ids is deprecated")
|
133
|
+
@listener.stubs(sqs: @sqs)
|
134
|
+
@listener.send(:read_messages)
|
135
|
+
end
|
136
|
+
|
137
|
+
def test_each_message_processor_is_yielded
|
138
|
+
messages_yielded = []
|
139
|
+
@listener = QueueListener.new(@topic_id) { |m| messages_yielded.push(m) }
|
140
|
+
@listener.stubs(sqs: @sqs)
|
141
|
+
@listener.send(:read_messages)
|
142
|
+
|
143
|
+
assert_equal messages_yielded.size, 2
|
144
|
+
assert messages_yielded.include?(@message1)
|
145
|
+
assert messages_yielded.include?(@message2)
|
146
|
+
end
|
147
|
+
end
|
90
148
|
end
|
@@ -45,9 +45,10 @@ module Propono
|
|
45
45
|
def test_processor_is_called_correctly
|
46
46
|
topic = "my-topic"
|
47
47
|
message = "my-message"
|
48
|
+
id = "qwe123"
|
48
49
|
processor = Proc.new {}
|
49
|
-
tcp_data = {topic: topic, message: message}.to_json
|
50
|
-
processor.expects(:call).with(topic, message)
|
50
|
+
tcp_data = {topic: topic, message: message, id: id}.to_json
|
51
|
+
processor.expects(:call).with(topic, message, {id: id})
|
51
52
|
|
52
53
|
listener = TcpListener.new(&processor)
|
53
54
|
listener.send(:process_tcp_data, tcp_data)
|
@@ -59,5 +60,17 @@ module Propono
|
|
59
60
|
listener.listen
|
60
61
|
end
|
61
62
|
end
|
62
|
-
end
|
63
63
|
|
64
|
+
class TcpListenerLegacyTest < Minitest::Test
|
65
|
+
def test_processor_is_called_correctly
|
66
|
+
topic = "my-topic"
|
67
|
+
message = "my-message"
|
68
|
+
processor = Proc.new {}
|
69
|
+
tcp_data = {topic: topic, message: message}.to_json
|
70
|
+
processor.expects(:call).with(topic, message)
|
71
|
+
|
72
|
+
listener = TcpListener.new(&processor)
|
73
|
+
listener.send(:process_tcp_data, tcp_data)
|
74
|
+
end
|
75
|
+
end
|
76
|
+
end
|
@@ -42,9 +42,10 @@ module Propono
|
|
42
42
|
def test_processor_is_called_correctly
|
43
43
|
topic = "my-topic"
|
44
44
|
message = "my-message"
|
45
|
+
id = "123asd"
|
45
46
|
processor = Proc.new {}
|
46
|
-
udp_data = {topic: topic, message: message}.to_json
|
47
|
-
processor.expects(:call).with(topic, message)
|
47
|
+
udp_data = {topic: topic, message: message, id: id}.to_json
|
48
|
+
processor.expects(:call).with(topic, message, {id: id})
|
48
49
|
|
49
50
|
server = UdpListener.new(&processor)
|
50
51
|
server.send(:process_udp_data, udp_data)
|
@@ -56,4 +57,17 @@ module Propono
|
|
56
57
|
listener.listen
|
57
58
|
end
|
58
59
|
end
|
60
|
+
|
61
|
+
class UdpListenerLegacyTest < Minitest::Test
|
62
|
+
def test_processor_is_called_correctly
|
63
|
+
topic = "my-topic"
|
64
|
+
message = "my-message"
|
65
|
+
processor = Proc.new {}
|
66
|
+
udp_data = {topic: topic, message: message}.to_json
|
67
|
+
processor.expects(:call).with(topic, message)
|
68
|
+
|
69
|
+
server = UdpListener.new(&processor)
|
70
|
+
server.send(:process_udp_data, udp_data)
|
71
|
+
end
|
72
|
+
end
|
59
73
|
end
|
data/test/test_helper.rb
CHANGED
metadata
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: propono
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 0.
|
4
|
+
version: 0.9.0
|
5
5
|
platform: ruby
|
6
6
|
authors:
|
7
7
|
- MalcyL
|
@@ -9,7 +9,7 @@ authors:
|
|
9
9
|
autorequire:
|
10
10
|
bindir: bin
|
11
11
|
cert_chain: []
|
12
|
-
date: 2013-11-
|
12
|
+
date: 2013-11-13 00:00:00.000000000 Z
|
13
13
|
dependencies:
|
14
14
|
- !ruby/object:Gem::Dependency
|
15
15
|
name: fog
|
@@ -119,6 +119,7 @@ files:
|
|
119
119
|
- lib/propono/components/sqs.rb
|
120
120
|
- lib/propono/components/topic.rb
|
121
121
|
- lib/propono/configuration.rb
|
122
|
+
- lib/propono/helpers/hash.rb
|
122
123
|
- lib/propono/logger.rb
|
123
124
|
- lib/propono/propono_error.rb
|
124
125
|
- lib/propono/services/publisher.rb
|
@@ -138,6 +139,7 @@ files:
|
|
138
139
|
- test/components/topic_test.rb
|
139
140
|
- test/config.yml.example
|
140
141
|
- test/configuration_test.rb
|
142
|
+
- test/helpers/hash_test.rb
|
141
143
|
- test/integration/integration_test.rb
|
142
144
|
- test/integration/sns_to_sqs_test.rb
|
143
145
|
- test/integration/tcp_to_sqs_test.rb
|
@@ -173,7 +175,7 @@ required_rubygems_version: !ruby/object:Gem::Requirement
|
|
173
175
|
version: '0'
|
174
176
|
requirements: []
|
175
177
|
rubyforge_project:
|
176
|
-
rubygems_version: 2.
|
178
|
+
rubygems_version: 2.1.9
|
177
179
|
signing_key:
|
178
180
|
specification_version: 4
|
179
181
|
summary: General purpose pub/sub library built on top of AWS SNS and SQS
|
@@ -186,6 +188,7 @@ test_files:
|
|
186
188
|
- test/components/topic_test.rb
|
187
189
|
- test/config.yml.example
|
188
190
|
- test/configuration_test.rb
|
191
|
+
- test/helpers/hash_test.rb
|
189
192
|
- test/integration/integration_test.rb
|
190
193
|
- test/integration/sns_to_sqs_test.rb
|
191
194
|
- test/integration/tcp_to_sqs_test.rb
|