active_projection 0.3.0 → 0.4.1
Sign up to get free protection for your applications and to get access to all the features.
- checksums.yaml +4 -4
- data/lib/active_projection/event_client.rb +10 -1
- data/lib/active_projection/projection_type.rb +48 -18
- data/lib/active_projection/projection_type_registry.rb +1 -1
- data/lib/active_projection/version.rb +1 -1
- data/spec/lib/projection_type_registry_spec.rb +4 -3
- data/spec/lib/projecton_type_spec.rb +8 -8
- metadata +4 -4
checksums.yaml
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
---
|
2
2
|
SHA1:
|
3
|
-
metadata.gz:
|
4
|
-
data.tar.gz:
|
3
|
+
metadata.gz: a6b4b40f0225e31820939e9bfe3148ea9f212e47
|
4
|
+
data.tar.gz: 0aa40406e3d1bb73fcf2073290b9154e67ed7e94
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: f6488612d653cdbba05c73f17276e73c534a1fdcb6d35c1740c536bdf87b3c950ffc5941a0059bd9f0afbea120db2d9be290c47c84df5b07cfa8a750c71de5a9
|
7
|
+
data.tar.gz: 49c4483a2904602e73395a14d5ad1ef731c53e5dba486e272caddbf9924a076480e137fbc6bac06e7b8a93fc4b7363eb9e4533625aedc5deb342ea457b620d05
|
@@ -21,6 +21,7 @@ module ActiveProjection
|
|
21
21
|
def listen_for_events
|
22
22
|
subscribe_to event_queue do |delivery_info, properties, body|
|
23
23
|
event_received properties, body
|
24
|
+
send_browser_notification properties.headers[:id]
|
24
25
|
end
|
25
26
|
end
|
26
27
|
|
@@ -35,6 +36,10 @@ module ActiveProjection
|
|
35
36
|
end
|
36
37
|
end
|
37
38
|
|
39
|
+
def send_browser_notification(id)
|
40
|
+
server_side_events_exchange.publish id.to_s
|
41
|
+
end
|
42
|
+
|
38
43
|
def send_request_for(id)
|
39
44
|
resend_request_exchange.publish id.to_s, routing_key: 'resend_request'
|
40
45
|
end
|
@@ -51,7 +56,7 @@ module ActiveProjection
|
|
51
56
|
def event_received(properties, body)
|
52
57
|
RELOADER.execute_if_updated
|
53
58
|
puts "Received #{properties.type} with #{body}"
|
54
|
-
ProjectionTypeRegistry.process properties.headers.deep_symbolize_keys
|
59
|
+
ProjectionTypeRegistry.process properties.headers.deep_symbolize_keys!, build_event(properties.type, JSON.parse(body))
|
55
60
|
end
|
56
61
|
|
57
62
|
def build_event(type, data)
|
@@ -94,6 +99,10 @@ module ActiveProjection
|
|
94
99
|
@resend_request_exchange ||= event_channel.direct "resend_request_#{options[:event_exchange]}"
|
95
100
|
end
|
96
101
|
|
102
|
+
def server_side_events_exchange
|
103
|
+
@server_side_events_exchange ||= event_channel.fanout "server_side_#{options[:event_exchange]}"
|
104
|
+
end
|
105
|
+
|
97
106
|
def options
|
98
107
|
@options
|
99
108
|
end
|
@@ -13,44 +13,74 @@ module ActiveProjection
|
|
13
13
|
end
|
14
14
|
self.class.public_instance_methods(false).each do |method_name|
|
15
15
|
method = self.class.instance_method method_name
|
16
|
-
|
17
|
-
|
18
|
-
handlers[event_type] << method.
|
16
|
+
raise WrongArgumentsCountError if 2 < method.arity or method.arity < 1
|
17
|
+
event_type = ProjectionType.method_name_to_event_type method_name
|
18
|
+
handlers[event_type] << [method_name, method.arity]
|
19
19
|
end
|
20
20
|
end
|
21
21
|
|
22
22
|
def evaluate(headers)
|
23
|
-
return false unless
|
24
|
-
last_id =
|
23
|
+
return false unless solid? || headers[:replayed]
|
24
|
+
last_id = fetch_last_id
|
25
|
+
event_id = headers[:id]
|
25
26
|
case
|
26
|
-
when last_id + 1 ==
|
27
|
-
ProjectionRepository.set_last_id projection_id, headers[:store_id]
|
28
|
-
puts "process this event"
|
27
|
+
when last_id + 1 == event_id
|
29
28
|
true
|
30
|
-
when last_id >=
|
31
|
-
puts "event already processed"
|
29
|
+
when last_id >= event_id
|
30
|
+
puts "[#{self.class.name}] event #{event_id} already processed"
|
32
31
|
false
|
33
|
-
when last_id <
|
34
|
-
|
35
|
-
|
32
|
+
when last_id < event_id
|
33
|
+
set_broken
|
34
|
+
puts "[#{self.class.name}] #{event_id - last_id} events are missing"
|
36
35
|
false
|
37
36
|
end
|
38
37
|
end
|
39
38
|
|
40
|
-
def invoke(event)
|
41
|
-
|
42
|
-
|
43
|
-
handlers[event_type].each do |method|
|
44
|
-
|
39
|
+
def invoke(event, headers)
|
40
|
+
event_id = headers[:id]
|
41
|
+
event_type = event.class.name.to_sym
|
42
|
+
handlers[event_type].each do |method, arity|
|
43
|
+
begin
|
44
|
+
if 1 == arity
|
45
|
+
self.send method, event
|
46
|
+
else
|
47
|
+
self.send method, event, headers
|
48
|
+
end
|
49
|
+
rescue Exception
|
50
|
+
puts "[#{self.class.name}] error processing #{event_type}[#{event_id}]"
|
51
|
+
raise
|
52
|
+
end
|
45
53
|
end
|
54
|
+
update_last_id event_id
|
55
|
+
puts "[#{self.class.name}] sucessfully processed #{event_type}[#{event_id}]"
|
46
56
|
end
|
47
57
|
|
48
58
|
private
|
49
59
|
attr_accessor :handlers
|
50
60
|
attr_writer :projection_id
|
51
61
|
|
62
|
+
def self.method_name_to_event_type(method_name)
|
63
|
+
method_name.to_s.gsub('__', '/').camelcase.to_sym
|
64
|
+
end
|
65
|
+
|
52
66
|
def projection_id
|
53
67
|
@projection_id ||= ProjectionRepository.create_or_get(self.class.name).id
|
54
68
|
end
|
69
|
+
|
70
|
+
def solid?
|
71
|
+
ProjectionRepository.solid? projection_id
|
72
|
+
end
|
73
|
+
|
74
|
+
def fetch_last_id
|
75
|
+
ProjectionRepository.get_last_id projection_id
|
76
|
+
end
|
77
|
+
|
78
|
+
def set_broken
|
79
|
+
ProjectionRepository.set_broken projection_id
|
80
|
+
end
|
81
|
+
|
82
|
+
def update_last_id(id)
|
83
|
+
ProjectionRepository.set_last_id projection_id, id
|
84
|
+
end
|
55
85
|
end
|
56
86
|
end
|
@@ -15,7 +15,7 @@ module ActiveProjection
|
|
15
15
|
def process(headers, event)
|
16
16
|
projections.each do |projection|
|
17
17
|
ActiveRecord::Base.transaction do
|
18
|
-
projection.invoke
|
18
|
+
projection.invoke(event, headers) if projection.evaluate headers
|
19
19
|
end
|
20
20
|
end
|
21
21
|
end
|
@@ -14,9 +14,10 @@ describe ActiveProjection::ProjectionTypeRegistry do
|
|
14
14
|
end
|
15
15
|
|
16
16
|
it 'invokes event handlers' do
|
17
|
+
headers = {}
|
17
18
|
event = TestEvent.new
|
18
|
-
expect_any_instance_of(TestProjection).to receive(:evaluate).with(
|
19
|
-
expect_any_instance_of(TestProjection).to receive(:invoke).with(event)
|
20
|
-
ActiveProjection::ProjectionTypeRegistry.process(
|
19
|
+
expect_any_instance_of(TestProjection).to receive(:evaluate).with(headers).and_return(true)
|
20
|
+
expect_any_instance_of(TestProjection).to receive(:invoke).with(event, headers)
|
21
|
+
ActiveProjection::ProjectionTypeRegistry.process(headers, event)
|
21
22
|
end
|
22
23
|
end
|
@@ -12,7 +12,7 @@ describe ActiveProjection::ProjectionType do
|
|
12
12
|
end
|
13
13
|
describe 'instance' do
|
14
14
|
class TestProjection
|
15
|
-
def test_event(event)
|
15
|
+
def test_event(event, headers)
|
16
16
|
end
|
17
17
|
|
18
18
|
def dummy_event(event)
|
@@ -40,7 +40,7 @@ describe ActiveProjection::ProjectionType do
|
|
40
40
|
it 'rejects processing, if projection is broken' do
|
41
41
|
expect(ActiveProjection::ProjectionRepository).to receive(:solid?).and_return(false)
|
42
42
|
expect(ActiveProjection::ProjectionRepository).to_not receive(:get_last_id)
|
43
|
-
@projection.evaluate({
|
43
|
+
@projection.evaluate({id: 1})
|
44
44
|
end
|
45
45
|
|
46
46
|
describe 'with solid projection' do
|
@@ -50,25 +50,25 @@ describe ActiveProjection::ProjectionType do
|
|
50
50
|
end
|
51
51
|
|
52
52
|
it 'processes event with the correct id' do
|
53
|
-
expect(
|
54
|
-
expect(@projection.evaluate({store_id: 6})).to be_true
|
53
|
+
expect(@projection.evaluate({id: 6})).to be_true
|
55
54
|
end
|
56
55
|
|
57
56
|
it 'rejects event with last id smaller event id' do
|
58
|
-
expect(@projection.evaluate({
|
57
|
+
expect(@projection.evaluate({id: 3})).to be_false
|
59
58
|
end
|
60
59
|
|
61
60
|
it 'rejects event with last greater equal event id' do
|
62
61
|
expect(ActiveProjection::ProjectionRepository).to receive(:set_broken).with(0)
|
63
|
-
expect(@projection.evaluate({
|
62
|
+
expect(@projection.evaluate({id: 7})).to be_false
|
64
63
|
end
|
65
64
|
end
|
66
65
|
end
|
67
66
|
|
68
67
|
it 'invokes all handler' do
|
68
|
+
expect(ActiveProjection::ProjectionRepository).to receive(:set_last_id).with(1, 6)
|
69
69
|
expect(@projection).to receive(:test_event)
|
70
|
-
expect(@projection).to_not receive(:
|
71
|
-
@projection.invoke(TestEvent.new)
|
70
|
+
expect(@projection).to_not receive(:dummy)
|
71
|
+
@projection.invoke(TestEvent.new, {id: 6})
|
72
72
|
end
|
73
73
|
end
|
74
74
|
end
|
metadata
CHANGED
@@ -1,14 +1,14 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: active_projection
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 0.
|
4
|
+
version: 0.4.1
|
5
5
|
platform: ruby
|
6
6
|
authors:
|
7
7
|
- Andreas Reischuck
|
8
8
|
autorequire:
|
9
9
|
bindir: bin
|
10
10
|
cert_chain: []
|
11
|
-
date: 2013-
|
11
|
+
date: 2013-11-21 00:00:00.000000000 Z
|
12
12
|
dependencies:
|
13
13
|
- !ruby/object:Gem::Dependency
|
14
14
|
name: active_event
|
@@ -16,14 +16,14 @@ dependencies:
|
|
16
16
|
requirements:
|
17
17
|
- - '='
|
18
18
|
- !ruby/object:Gem::Version
|
19
|
-
version: 0.
|
19
|
+
version: 0.4.1
|
20
20
|
type: :runtime
|
21
21
|
prerelease: false
|
22
22
|
version_requirements: !ruby/object:Gem::Requirement
|
23
23
|
requirements:
|
24
24
|
- - '='
|
25
25
|
- !ruby/object:Gem::Version
|
26
|
-
version: 0.
|
26
|
+
version: 0.4.1
|
27
27
|
- !ruby/object:Gem::Dependency
|
28
28
|
name: activerecord
|
29
29
|
requirement: !ruby/object:Gem::Requirement
|