pub_sub_model_sync 0.2.4 → 0.3.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/.idea/.gitignore +8 -0
- data/.idea/.rakeTasks +7 -0
- data/.idea/codeStyles/codeStyleConfig.xml +5 -0
- data/.idea/encodings.xml +4 -0
- data/.idea/inspectionProfiles/Project_Default.xml +16 -0
- data/.idea/misc.xml +7 -0
- data/.idea/modules.xml +8 -0
- data/.idea/pub_sub_model_sync.iml +96 -0
- data/.idea/vcs.xml +6 -0
- data/CHANGELOG.md +4 -0
- data/Gemfile +4 -0
- data/Gemfile.lock +6 -1
- data/README.md +49 -18
- data/lib/pub_sub_model_sync/connector.rb +0 -1
- data/lib/pub_sub_model_sync/message_processor.rb +20 -12
- data/lib/pub_sub_model_sync/publisher.rb +7 -13
- data/lib/pub_sub_model_sync/publisher_concern.rb +9 -9
- data/lib/pub_sub_model_sync/service_base.rb +2 -2
- data/lib/pub_sub_model_sync/subscriber_concern.rb +7 -8
- data/lib/pub_sub_model_sync/version.rb +1 -1
- metadata +11 -2
checksums.yaml
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
---
|
|
2
2
|
SHA256:
|
|
3
|
-
metadata.gz:
|
|
4
|
-
data.tar.gz:
|
|
3
|
+
metadata.gz: 04acaa2b5befa05fd52978367afdb24c6a1a5858e10441620a2860a57ea9cd55
|
|
4
|
+
data.tar.gz: 25297748dd5e1099f9f251d73f7f94c0680e9c04820c3396143f9b3ca17170ad
|
|
5
5
|
SHA512:
|
|
6
|
-
metadata.gz:
|
|
7
|
-
data.tar.gz:
|
|
6
|
+
metadata.gz: dea58e39fd6d77599000a932f7db942052d5309069c8adb0e571fcb2b7be4a5d4429048371b5bac51c18ff9f016dc88fc0e85ea73ca04bc93f36536c580ea544
|
|
7
|
+
data.tar.gz: cead04daf416641b5d900d4c8c6a13509c49fa8256dd343552c70b578f5af3a3ba39465069999688418e4de60ba4f9a62b4e40e3b54c0c55dd89dcf366f28ab2
|
data/.idea/.gitignore
ADDED
data/.idea/.rakeTasks
ADDED
|
@@ -0,0 +1,7 @@
|
|
|
1
|
+
<?xml version="1.0" encoding="UTF-8"?>
|
|
2
|
+
<Settings><!--This file was automatically generated by Ruby plugin.
|
|
3
|
+
You are allowed to:
|
|
4
|
+
1. Remove rake task
|
|
5
|
+
2. Add existing rake tasks
|
|
6
|
+
To add existing rake tasks automatically delete this file and reload the project.
|
|
7
|
+
--><RakeGroup description="" fullCmd="" taksId="rake"><RakeTask description="Build pub_sub_model_sync-0.1.0.gem into the pkg directory" fullCmd="build" taksId="build" /><RakeTask description="Remove any temporary products" fullCmd="clean" taksId="clean" /><RakeTask description="Remove any generated files" fullCmd="clobber" taksId="clobber" /><RakeTask description="Build and install pub_sub_model_sync-0.1.0.gem into system gems" fullCmd="install" taksId="install" /><RakeGroup description="" fullCmd="" taksId="install"><RakeTask description="Build and install pub_sub_model_sync-0.1.0.gem into system gems without network access" fullCmd="install:local" taksId="local" /></RakeGroup><RakeTask description="Create tag v0.1.0 and build and push pub_sub_model_sync-0.1.0.gem to TODO: Set to 'http://mygemserver.com'" fullCmd="release[remote]" taksId="release[remote]" /><RakeTask description="Run RSpec code examples" fullCmd="spec" taksId="spec" /><RakeTask description="" fullCmd="default" taksId="default" /><RakeTask description="" fullCmd="release" taksId="release" /><RakeGroup description="" fullCmd="" taksId="release"><RakeTask description="" fullCmd="release:guard_clean" taksId="guard_clean" /><RakeTask description="" fullCmd="release:rubygem_push" taksId="rubygem_push" /><RakeTask description="" fullCmd="release:source_control_push" taksId="source_control_push" /></RakeGroup></RakeGroup></Settings>
|
data/.idea/encodings.xml
ADDED
|
@@ -0,0 +1,16 @@
|
|
|
1
|
+
<component name="InspectionProjectProfileManager">
|
|
2
|
+
<profile version="1.0">
|
|
3
|
+
<option name="myName" value="Project Default" />
|
|
4
|
+
<inspection_tool class="Rubocop" enabled="true" level="WARNING" enabled_by_default="true">
|
|
5
|
+
<option name="mySeverityMap">
|
|
6
|
+
<map>
|
|
7
|
+
<entry key="convention" value="ERROR" />
|
|
8
|
+
<entry key="error" value="ERROR" />
|
|
9
|
+
<entry key="fatal" value="ERROR" />
|
|
10
|
+
<entry key="refactor" value="ERROR" />
|
|
11
|
+
<entry key="warning" value="ERROR" />
|
|
12
|
+
</map>
|
|
13
|
+
</option>
|
|
14
|
+
</inspection_tool>
|
|
15
|
+
</profile>
|
|
16
|
+
</component>
|
data/.idea/misc.xml
ADDED
|
@@ -0,0 +1,7 @@
|
|
|
1
|
+
<?xml version="1.0" encoding="UTF-8"?>
|
|
2
|
+
<project version="4">
|
|
3
|
+
<component name="JavaScriptSettings">
|
|
4
|
+
<option name="languageLevel" value="ES6" />
|
|
5
|
+
</component>
|
|
6
|
+
<component name="ProjectRootManager" version="2" project-jdk-name="RVM: ruby-2.5.3" project-jdk-type="RUBY_SDK" />
|
|
7
|
+
</project>
|
data/.idea/modules.xml
ADDED
|
@@ -0,0 +1,8 @@
|
|
|
1
|
+
<?xml version="1.0" encoding="UTF-8"?>
|
|
2
|
+
<project version="4">
|
|
3
|
+
<component name="ProjectModuleManager">
|
|
4
|
+
<modules>
|
|
5
|
+
<module fileurl="file://$PROJECT_DIR$/.idea/pub_sub_model_sync.iml" filepath="$PROJECT_DIR$/.idea/pub_sub_model_sync.iml" />
|
|
6
|
+
</modules>
|
|
7
|
+
</component>
|
|
8
|
+
</project>
|
|
@@ -0,0 +1,96 @@
|
|
|
1
|
+
<?xml version="1.0" encoding="UTF-8"?>
|
|
2
|
+
<module type="RUBY_MODULE" version="4">
|
|
3
|
+
<component name="ModuleRunConfigurationManager">
|
|
4
|
+
<shared />
|
|
5
|
+
</component>
|
|
6
|
+
<component name="NewModuleRootManager">
|
|
7
|
+
<content url="file://$MODULE_DIR$" />
|
|
8
|
+
<orderEntry type="jdk" jdkName="RVM: ruby-2.6.5" jdkType="RUBY_SDK" />
|
|
9
|
+
<orderEntry type="sourceFolder" forTests="false" />
|
|
10
|
+
<orderEntry type="library" scope="PROVIDED" name="actioncable (v6.0.2.2, RVM: ruby-2.6.5) [gem]" level="application" />
|
|
11
|
+
<orderEntry type="library" scope="PROVIDED" name="actionmailbox (v6.0.2.2, RVM: ruby-2.6.5) [gem]" level="application" />
|
|
12
|
+
<orderEntry type="library" scope="PROVIDED" name="actionmailer (v6.0.2.2, RVM: ruby-2.6.5) [gem]" level="application" />
|
|
13
|
+
<orderEntry type="library" scope="PROVIDED" name="actionpack (v6.0.2.2, RVM: ruby-2.6.5) [gem]" level="application" />
|
|
14
|
+
<orderEntry type="library" scope="PROVIDED" name="actiontext (v6.0.2.2, RVM: ruby-2.6.5) [gem]" level="application" />
|
|
15
|
+
<orderEntry type="library" scope="PROVIDED" name="actionview (v6.0.2.2, RVM: ruby-2.6.5) [gem]" level="application" />
|
|
16
|
+
<orderEntry type="library" scope="PROVIDED" name="activejob (v6.0.2.2, RVM: ruby-2.6.5) [gem]" level="application" />
|
|
17
|
+
<orderEntry type="library" scope="PROVIDED" name="activemodel (v6.0.2.2, RVM: ruby-2.6.5) [gem]" level="application" />
|
|
18
|
+
<orderEntry type="library" scope="PROVIDED" name="activerecord (v6.0.2.2, RVM: ruby-2.6.5) [gem]" level="application" />
|
|
19
|
+
<orderEntry type="library" scope="PROVIDED" name="activestorage (v6.0.2.2, RVM: ruby-2.6.5) [gem]" level="application" />
|
|
20
|
+
<orderEntry type="library" scope="PROVIDED" name="activesupport (v6.0.2.2, RVM: ruby-2.6.5) [gem]" level="application" />
|
|
21
|
+
<orderEntry type="library" scope="PROVIDED" name="addressable (v2.7.0, RVM: ruby-2.6.5) [gem]" level="application" />
|
|
22
|
+
<orderEntry type="library" scope="PROVIDED" name="amq-protocol (v2.3.0, RVM: ruby-2.6.5) [gem]" level="application" />
|
|
23
|
+
<orderEntry type="library" scope="PROVIDED" name="ast (v2.4.0, RVM: ruby-2.6.5) [gem]" level="application" />
|
|
24
|
+
<orderEntry type="library" scope="PROVIDED" name="builder (v3.2.4, RVM: ruby-2.6.5) [gem]" level="application" />
|
|
25
|
+
<orderEntry type="library" scope="PROVIDED" name="bundler (v2.1.4, RVM: ruby-2.6.5) [gem]" level="application" />
|
|
26
|
+
<orderEntry type="library" scope="PROVIDED" name="bunny (v2.14.3, RVM: ruby-2.6.5) [gem]" level="application" />
|
|
27
|
+
<orderEntry type="library" scope="PROVIDED" name="concurrent-ruby (v1.1.6, RVM: ruby-2.6.5) [gem]" level="application" />
|
|
28
|
+
<orderEntry type="library" scope="PROVIDED" name="crass (v1.0.6, RVM: ruby-2.6.5) [gem]" level="application" />
|
|
29
|
+
<orderEntry type="library" scope="PROVIDED" name="database_cleaner (v1.8.4, RVM: ruby-2.6.5) [gem]" level="application" />
|
|
30
|
+
<orderEntry type="library" scope="PROVIDED" name="database_cleaner-active_record (v1.8.0, RVM: ruby-2.6.5) [gem]" level="application" />
|
|
31
|
+
<orderEntry type="library" scope="PROVIDED" name="diff-lcs (v1.3, RVM: ruby-2.6.5) [gem]" level="application" />
|
|
32
|
+
<orderEntry type="library" scope="PROVIDED" name="digest-crc (v0.5.1, RVM: ruby-2.6.5) [gem]" level="application" />
|
|
33
|
+
<orderEntry type="library" scope="PROVIDED" name="erubi (v1.9.0, RVM: ruby-2.6.5) [gem]" level="application" />
|
|
34
|
+
<orderEntry type="library" scope="PROVIDED" name="faraday (v0.17.3, RVM: ruby-2.6.5) [gem]" level="application" />
|
|
35
|
+
<orderEntry type="library" scope="PROVIDED" name="globalid (v0.4.2, RVM: ruby-2.6.5) [gem]" level="application" />
|
|
36
|
+
<orderEntry type="library" scope="PROVIDED" name="google-cloud-core (v1.3.2, RVM: ruby-2.6.5) [gem]" level="application" />
|
|
37
|
+
<orderEntry type="library" scope="PROVIDED" name="google-cloud-env (v1.2.1, RVM: ruby-2.6.5) [gem]" level="application" />
|
|
38
|
+
<orderEntry type="library" scope="PROVIDED" name="google-cloud-pubsub (v1.0.2, RVM: ruby-2.6.5) [gem]" level="application" />
|
|
39
|
+
<orderEntry type="library" scope="PROVIDED" name="google-gax (v1.7.1, RVM: ruby-2.6.5) [gem]" level="application" />
|
|
40
|
+
<orderEntry type="library" scope="PROVIDED" name="google-protobuf (v3.11.4, RVM: ruby-2.6.5) [gem]" level="application" />
|
|
41
|
+
<orderEntry type="library" scope="PROVIDED" name="googleapis-common-protos (v1.3.9, RVM: ruby-2.6.5) [gem]" level="application" />
|
|
42
|
+
<orderEntry type="library" scope="PROVIDED" name="googleapis-common-protos-types (v1.0.4, RVM: ruby-2.6.5) [gem]" level="application" />
|
|
43
|
+
<orderEntry type="library" scope="PROVIDED" name="googleauth (v0.9.0, RVM: ruby-2.6.5) [gem]" level="application" />
|
|
44
|
+
<orderEntry type="library" scope="PROVIDED" name="grpc (v1.27.0, RVM: ruby-2.6.5) [gem]" level="application" />
|
|
45
|
+
<orderEntry type="library" scope="PROVIDED" name="grpc-google-iam-v1 (v0.6.9, RVM: ruby-2.6.5) [gem]" level="application" />
|
|
46
|
+
<orderEntry type="library" scope="PROVIDED" name="i18n (v1.8.2, RVM: ruby-2.6.5) [gem]" level="application" />
|
|
47
|
+
<orderEntry type="library" scope="PROVIDED" name="jaro_winkler (v1.5.4, RVM: ruby-2.6.5) [gem]" level="application" />
|
|
48
|
+
<orderEntry type="library" scope="PROVIDED" name="jwt (v2.2.1, RVM: ruby-2.6.5) [gem]" level="application" />
|
|
49
|
+
<orderEntry type="library" scope="PROVIDED" name="loofah (v2.5.0, RVM: ruby-2.6.5) [gem]" level="application" />
|
|
50
|
+
<orderEntry type="library" scope="PROVIDED" name="mail (v2.7.1, RVM: ruby-2.6.5) [gem]" level="application" />
|
|
51
|
+
<orderEntry type="library" scope="PROVIDED" name="marcel (v0.3.3, RVM: ruby-2.6.5) [gem]" level="application" />
|
|
52
|
+
<orderEntry type="library" scope="PROVIDED" name="memoist (v0.16.2, RVM: ruby-2.6.5) [gem]" level="application" />
|
|
53
|
+
<orderEntry type="library" scope="PROVIDED" name="method_source (v1.0.0, RVM: ruby-2.6.5) [gem]" level="application" />
|
|
54
|
+
<orderEntry type="library" scope="PROVIDED" name="mimemagic (v0.3.4, RVM: ruby-2.6.5) [gem]" level="application" />
|
|
55
|
+
<orderEntry type="library" scope="PROVIDED" name="mini_mime (v1.0.2, RVM: ruby-2.6.5) [gem]" level="application" />
|
|
56
|
+
<orderEntry type="library" scope="PROVIDED" name="mini_portile2 (v2.4.0, RVM: ruby-2.6.5) [gem]" level="application" />
|
|
57
|
+
<orderEntry type="library" scope="PROVIDED" name="minitest (v5.14.0, RVM: ruby-2.6.5) [gem]" level="application" />
|
|
58
|
+
<orderEntry type="library" scope="PROVIDED" name="multi_json (v1.14.1, RVM: ruby-2.6.5) [gem]" level="application" />
|
|
59
|
+
<orderEntry type="library" scope="PROVIDED" name="multipart-post (v2.1.1, RVM: ruby-2.6.5) [gem]" level="application" />
|
|
60
|
+
<orderEntry type="library" scope="PROVIDED" name="nio4r (v2.5.2, RVM: ruby-2.6.5) [gem]" level="application" />
|
|
61
|
+
<orderEntry type="library" scope="PROVIDED" name="nokogiri (v1.10.9, RVM: ruby-2.6.5) [gem]" level="application" />
|
|
62
|
+
<orderEntry type="library" scope="PROVIDED" name="os (v1.0.1, RVM: ruby-2.6.5) [gem]" level="application" />
|
|
63
|
+
<orderEntry type="library" scope="PROVIDED" name="parallel (v1.19.1, RVM: ruby-2.6.5) [gem]" level="application" />
|
|
64
|
+
<orderEntry type="library" scope="PROVIDED" name="parser (v2.7.0.4, RVM: ruby-2.6.5) [gem]" level="application" />
|
|
65
|
+
<orderEntry type="library" scope="PROVIDED" name="public_suffix (v4.0.3, RVM: ruby-2.6.5) [gem]" level="application" />
|
|
66
|
+
<orderEntry type="library" scope="PROVIDED" name="rack (v2.2.2, RVM: ruby-2.6.5) [gem]" level="application" />
|
|
67
|
+
<orderEntry type="library" scope="PROVIDED" name="rack-test (v1.1.0, RVM: ruby-2.6.5) [gem]" level="application" />
|
|
68
|
+
<orderEntry type="library" scope="PROVIDED" name="rails (v6.0.2.2, RVM: ruby-2.6.5) [gem]" level="application" />
|
|
69
|
+
<orderEntry type="library" scope="PROVIDED" name="rails-dom-testing (v2.0.3, RVM: ruby-2.6.5) [gem]" level="application" />
|
|
70
|
+
<orderEntry type="library" scope="PROVIDED" name="rails-html-sanitizer (v1.3.0, RVM: ruby-2.6.5) [gem]" level="application" />
|
|
71
|
+
<orderEntry type="library" scope="PROVIDED" name="railties (v6.0.2.2, RVM: ruby-2.6.5) [gem]" level="application" />
|
|
72
|
+
<orderEntry type="library" scope="PROVIDED" name="rainbow (v3.0.0, RVM: ruby-2.6.5) [gem]" level="application" />
|
|
73
|
+
<orderEntry type="library" scope="PROVIDED" name="rake (v13.0.1, RVM: ruby-2.6.5) [gem]" level="application" />
|
|
74
|
+
<orderEntry type="library" scope="PROVIDED" name="rexml (v3.2.4, RVM: ruby-2.6.5) [gem]" level="application" />
|
|
75
|
+
<orderEntry type="library" scope="PROVIDED" name="rly (v0.2.3, RVM: ruby-2.6.5) [gem]" level="application" />
|
|
76
|
+
<orderEntry type="library" scope="PROVIDED" name="rspec (v3.9.0, RVM: ruby-2.6.5) [gem]" level="application" />
|
|
77
|
+
<orderEntry type="library" scope="PROVIDED" name="rspec-core (v3.9.1, RVM: ruby-2.6.5) [gem]" level="application" />
|
|
78
|
+
<orderEntry type="library" scope="PROVIDED" name="rspec-expectations (v3.9.0, RVM: ruby-2.6.5) [gem]" level="application" />
|
|
79
|
+
<orderEntry type="library" scope="PROVIDED" name="rspec-mocks (v3.9.1, RVM: ruby-2.6.5) [gem]" level="application" />
|
|
80
|
+
<orderEntry type="library" scope="PROVIDED" name="rspec-support (v3.9.2, RVM: ruby-2.6.5) [gem]" level="application" />
|
|
81
|
+
<orderEntry type="library" scope="PROVIDED" name="rubocop (v0.80.1, RVM: ruby-2.6.5) [gem]" level="application" />
|
|
82
|
+
<orderEntry type="library" scope="PROVIDED" name="ruby-kafka (v1.0.0, RVM: ruby-2.6.5) [gem]" level="application" />
|
|
83
|
+
<orderEntry type="library" scope="PROVIDED" name="ruby-progressbar (v1.10.1, RVM: ruby-2.6.5) [gem]" level="application" />
|
|
84
|
+
<orderEntry type="library" scope="PROVIDED" name="signet (v0.11.0, RVM: ruby-2.6.5) [gem]" level="application" />
|
|
85
|
+
<orderEntry type="library" scope="PROVIDED" name="sprockets (v4.0.0, RVM: ruby-2.6.5) [gem]" level="application" />
|
|
86
|
+
<orderEntry type="library" scope="PROVIDED" name="sprockets-rails (v3.2.1, RVM: ruby-2.6.5) [gem]" level="application" />
|
|
87
|
+
<orderEntry type="library" scope="PROVIDED" name="sqlite3 (v1.4.2, RVM: ruby-2.6.5) [gem]" level="application" />
|
|
88
|
+
<orderEntry type="library" scope="PROVIDED" name="thor (v1.0.1, RVM: ruby-2.6.5) [gem]" level="application" />
|
|
89
|
+
<orderEntry type="library" scope="PROVIDED" name="thread_safe (v0.3.6, RVM: ruby-2.6.5) [gem]" level="application" />
|
|
90
|
+
<orderEntry type="library" scope="PROVIDED" name="tzinfo (v1.2.7, RVM: ruby-2.6.5) [gem]" level="application" />
|
|
91
|
+
<orderEntry type="library" scope="PROVIDED" name="unicode-display_width (v1.6.1, RVM: ruby-2.6.5) [gem]" level="application" />
|
|
92
|
+
<orderEntry type="library" scope="PROVIDED" name="websocket-driver (v0.7.1, RVM: ruby-2.6.5) [gem]" level="application" />
|
|
93
|
+
<orderEntry type="library" scope="PROVIDED" name="websocket-extensions (v0.1.4, RVM: ruby-2.6.5) [gem]" level="application" />
|
|
94
|
+
<orderEntry type="library" scope="PROVIDED" name="zeitwerk (v2.3.0, RVM: ruby-2.6.5) [gem]" level="application" />
|
|
95
|
+
</component>
|
|
96
|
+
</module>
|
data/.idea/vcs.xml
ADDED
data/CHANGELOG.md
CHANGED
data/Gemfile
CHANGED
data/Gemfile.lock
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
PATH
|
|
2
2
|
remote: .
|
|
3
3
|
specs:
|
|
4
|
-
pub_sub_model_sync (0.
|
|
4
|
+
pub_sub_model_sync (0.3.0)
|
|
5
5
|
activesupport
|
|
6
6
|
rails
|
|
7
7
|
|
|
@@ -72,6 +72,10 @@ GEM
|
|
|
72
72
|
amq-protocol (~> 2.3, >= 2.3.0)
|
|
73
73
|
concurrent-ruby (1.1.6)
|
|
74
74
|
crass (1.0.6)
|
|
75
|
+
database_cleaner (1.8.4)
|
|
76
|
+
database_cleaner-active_record (1.8.0)
|
|
77
|
+
activerecord
|
|
78
|
+
database_cleaner (~> 1.8.0)
|
|
75
79
|
diff-lcs (1.3)
|
|
76
80
|
digest-crc (0.5.1)
|
|
77
81
|
erubi (1.9.0)
|
|
@@ -228,6 +232,7 @@ PLATFORMS
|
|
|
228
232
|
DEPENDENCIES
|
|
229
233
|
bundler
|
|
230
234
|
bunny
|
|
235
|
+
database_cleaner-active_record
|
|
231
236
|
google-cloud-pubsub
|
|
232
237
|
pub_sub_model_sync!
|
|
233
238
|
rake
|
data/README.md
CHANGED
|
@@ -67,7 +67,7 @@ And then execute: $ bundle install
|
|
|
67
67
|
# attributes: name email age
|
|
68
68
|
class User < ActiveRecord::Base
|
|
69
69
|
include PubSubModelSync::PublisherConcern
|
|
70
|
-
ps_publish(%i[name email])
|
|
70
|
+
ps_publish(%i[id name email])
|
|
71
71
|
end
|
|
72
72
|
|
|
73
73
|
# App 2 (Subscriber)
|
|
@@ -95,7 +95,7 @@ PubSubModelSync::Publisher.new.publish_data(User, { msg: 'Hello' }, :greeting) #
|
|
|
95
95
|
class User < ActiveRecord::Base
|
|
96
96
|
self.table_name = 'publisher_users'
|
|
97
97
|
include PubSubModelSync::PublisherConcern
|
|
98
|
-
ps_publish(%i[name:full_name email], actions: %i[update], as_klass: 'Client'
|
|
98
|
+
ps_publish(%i[id:client_id name:full_name email], actions: %i[update], as_klass: 'Client')
|
|
99
99
|
|
|
100
100
|
def ps_skip_callback?(_action)
|
|
101
101
|
false # here logic with action to skip push message
|
|
@@ -110,12 +110,17 @@ end
|
|
|
110
110
|
class User < ActiveRecord::Base
|
|
111
111
|
self.table_name = 'subscriber_users'
|
|
112
112
|
include PubSubModelSync::SubscriberConcern
|
|
113
|
-
ps_subscribe(%i[name], actions: %i[update], as_klass: 'Client', id:
|
|
113
|
+
ps_subscribe(%i[name], actions: %i[update], as_klass: 'Client', id: %i[client_id email])
|
|
114
114
|
ps_class_subscribe(:greeting, as_action: :custom_greeting, as_klass: 'CustomUser')
|
|
115
|
+
alias_attribute :full_name, :name
|
|
115
116
|
|
|
116
117
|
def self.greeting(data)
|
|
117
118
|
puts 'Class message called through custom_greeting'
|
|
118
119
|
end
|
|
120
|
+
|
|
121
|
+
# def self.ps_find_model(data, settings)
|
|
122
|
+
# where(email: data[:email], ...).first_or_initialize
|
|
123
|
+
# end
|
|
119
124
|
end
|
|
120
125
|
```
|
|
121
126
|
|
|
@@ -132,6 +137,39 @@ end
|
|
|
132
137
|
```
|
|
133
138
|
|
|
134
139
|
## API
|
|
140
|
+
### Subscribers
|
|
141
|
+
- Permit to configure class level listeners
|
|
142
|
+
```ps_class_subscribe(action_name, as_action: nil, as_klass: nil)```
|
|
143
|
+
* as_action: (Optional) Source method name
|
|
144
|
+
* as_klass: (Optional) Source class name
|
|
145
|
+
|
|
146
|
+
- Permit to configure instance level listeners (CRUD)
|
|
147
|
+
```ps_subscribe(attrs, as_klass: nil, actions: nil, id: nil)```
|
|
148
|
+
* attrs: (Array/Required) Array of all attributes to be synced
|
|
149
|
+
* as_klass: (String/Optional) Source class name (Instead of the model class name, will use this value)
|
|
150
|
+
* actions: (Array/Optional, default: create/update/destroy) permit to customize action names
|
|
151
|
+
* id: (Sym|Array/Optional, default: id) Attr identifier(s) to find the corresponding model
|
|
152
|
+
|
|
153
|
+
- Permit to configure a custom model finder
|
|
154
|
+
```ps_find_model(data, settings)```
|
|
155
|
+
* data: (Hash) Data received from sync
|
|
156
|
+
* settings: (Hash(:klass, :action)) Class and action name from sync
|
|
157
|
+
Must return an existent or a new model object
|
|
158
|
+
|
|
159
|
+
- Get crud subscription configured for the class
|
|
160
|
+
```User.ps_subscriber(action_name)```
|
|
161
|
+
* action_name (default :create, :sym): can be :create, :update, :destroy
|
|
162
|
+
|
|
163
|
+
- Inspect all configured listeners
|
|
164
|
+
```PubSubModelSync::Config.listeners```
|
|
165
|
+
|
|
166
|
+
### Publishers
|
|
167
|
+
- Permit to configure crud publishers
|
|
168
|
+
```ps_publish(attrs, actions: nil, as_klass: nil)```
|
|
169
|
+
* attrs: (Array/Required) Array of attributes to be published
|
|
170
|
+
* actions: (Array/Optional, default: create/update/destroy) permit to customize action names
|
|
171
|
+
* as_klass: (String/Optional) Output class name (Instead of the model class name, will use this value)
|
|
172
|
+
|
|
135
173
|
- Permit to cancel sync called after create/update/destroy (Before initializing sync service)
|
|
136
174
|
```model.ps_skip_callback?(action)```
|
|
137
175
|
Note: Return true to cancel sync
|
|
@@ -150,29 +188,24 @@ end
|
|
|
150
188
|
- Perform sync on demand (:create, :update, :destroy):
|
|
151
189
|
The target model will receive a notification to perform the indicated action
|
|
152
190
|
```my_model.ps_perform_sync(action_name, custom_settings = {})```
|
|
153
|
-
* custom_settings: override default settings defined for action_name ({ attrs: [], as_klass: nil
|
|
191
|
+
* custom_settings: override default settings defined for action_name ({ attrs: [], as_klass: nil })
|
|
154
192
|
|
|
155
|
-
-
|
|
193
|
+
- Publish a class level notification:
|
|
156
194
|
```User.ps_class_publish(data, action: action_name, as_klass: custom_klass_name)```
|
|
157
195
|
Target class ```User.action_name``` will be called when message is received
|
|
158
196
|
* data: (required, :hash) message value to deliver
|
|
159
|
-
* action_name: (required, :sim)
|
|
160
|
-
* as_klass: (optional, :string)
|
|
197
|
+
* action_name: (required, :sim) Action name
|
|
198
|
+
* as_klass: (optional, :string) Custom class name (Default current model name)
|
|
161
199
|
|
|
162
|
-
-
|
|
200
|
+
- Publish a class level notification (Same as above: on demand call)
|
|
163
201
|
```PubSubModelSync::Publisher.new.publish_data(Klass_name, data, action_name)```
|
|
164
202
|
* klass_name: (required, Class) same class name as defined in ps_class_subscribe(...)
|
|
165
203
|
* data: (required, :hash) message value to deliver
|
|
166
204
|
* action_name: (required, :sim) same action name as defined in ps_class_subscribe(...)
|
|
167
205
|
|
|
168
|
-
- Get crud subscription configured for the class
|
|
169
|
-
```User.ps_subscriber(action_name)```
|
|
170
|
-
* action_name (default :create, :sym): can be :create, :update, :destroy
|
|
171
206
|
- Get crud publisher configured for the class
|
|
172
207
|
```User.ps_publisher(action_name)```
|
|
173
208
|
* action_name (default :create, :sym): can be :create, :update, :destroy
|
|
174
|
-
- Inspect all configured listeners
|
|
175
|
-
```PubSubModelSync::Config.listeners```
|
|
176
209
|
|
|
177
210
|
## Testing with RSpec
|
|
178
211
|
- Config: (spec/rails_helper.rb)
|
|
@@ -205,12 +238,10 @@ end
|
|
|
205
238
|
# Subscriber
|
|
206
239
|
it 'receive model message' do
|
|
207
240
|
action = :create
|
|
208
|
-
data = { name: 'name' }
|
|
209
|
-
|
|
210
|
-
attrs = PubSubModelSync::Publisher.build_attrs('User', action, user_id)
|
|
211
|
-
publisher = PubSubModelSync::MessageProcessor.new(data, 'User', action, id: user_id)
|
|
241
|
+
data = { name: 'name', id: 999 }
|
|
242
|
+
publisher = PubSubModelSync::MessageProcessor.new(data, 'User', action)
|
|
212
243
|
publisher.process
|
|
213
|
-
expect(User.where(id:
|
|
244
|
+
expect(User.where(id: data[:id]).any?).to be_truth
|
|
214
245
|
end
|
|
215
246
|
|
|
216
247
|
it 'receive class message' do
|
|
@@ -2,19 +2,18 @@
|
|
|
2
2
|
|
|
3
3
|
module PubSubModelSync
|
|
4
4
|
class MessageProcessor
|
|
5
|
-
attr_accessor :data, :
|
|
5
|
+
attr_accessor :data, :settings, :message_id
|
|
6
6
|
|
|
7
7
|
# @param data (Hash): any hash value to deliver
|
|
8
|
-
|
|
9
|
-
def initialize(data, klass, action, settings = {})
|
|
8
|
+
def initialize(data, klass, action)
|
|
10
9
|
@data = data
|
|
11
|
-
@settings =
|
|
12
|
-
@
|
|
10
|
+
@settings = { klass: klass, action: action }
|
|
11
|
+
@message_id = [klass, action, Time.current.to_i].join('-')
|
|
13
12
|
end
|
|
14
13
|
|
|
15
14
|
def process
|
|
16
15
|
@failed = false
|
|
17
|
-
log
|
|
16
|
+
log "processing message: #{[data, settings]}"
|
|
18
17
|
listeners = filter_listeners
|
|
19
18
|
return log 'Skipped: No listeners' unless listeners.any?
|
|
20
19
|
|
|
@@ -45,7 +44,7 @@ module PubSubModelSync
|
|
|
45
44
|
# support for: create, update, destroy
|
|
46
45
|
def call_listener(listener)
|
|
47
46
|
model = find_model(listener)
|
|
48
|
-
if
|
|
47
|
+
if settings[:action].to_sym == :destroy
|
|
49
48
|
model.destroy!
|
|
50
49
|
else
|
|
51
50
|
populate_model(model, listener)
|
|
@@ -58,8 +57,17 @@ module PubSubModelSync
|
|
|
58
57
|
|
|
59
58
|
def find_model(listener)
|
|
60
59
|
model_class = listener[:klass].constantize
|
|
61
|
-
|
|
62
|
-
|
|
60
|
+
if model_class.respond_to?(:ps_find_model)
|
|
61
|
+
return model_class.ps_find_model(data, settings)
|
|
62
|
+
end
|
|
63
|
+
|
|
64
|
+
model_class.where(model_identifiers(listener)).first_or_initialize
|
|
65
|
+
end
|
|
66
|
+
|
|
67
|
+
def model_identifiers(listener)
|
|
68
|
+
identifiers = listener[:settings][:id]
|
|
69
|
+
identifiers = [identifiers] unless identifiers.is_a?(Array)
|
|
70
|
+
identifiers.map { |key| [key, data[key.to_sym]] }.to_h
|
|
63
71
|
end
|
|
64
72
|
|
|
65
73
|
def populate_model(model, listener)
|
|
@@ -72,13 +80,13 @@ module PubSubModelSync
|
|
|
72
80
|
def filter_listeners
|
|
73
81
|
listeners = PubSubModelSync::Config.listeners
|
|
74
82
|
listeners.select do |listener|
|
|
75
|
-
listener[:as_klass].to_s ==
|
|
76
|
-
listener[:as_action].to_s ==
|
|
83
|
+
listener[:as_klass].to_s == settings[:klass].to_s &&
|
|
84
|
+
listener[:as_action].to_s == settings[:action].to_s
|
|
77
85
|
end
|
|
78
86
|
end
|
|
79
87
|
|
|
80
88
|
def log(message, kind = :info)
|
|
81
|
-
PubSubModelSync::Config.log "#{
|
|
89
|
+
PubSubModelSync::Config.log "(ID: #{message_id}) #{message}", kind
|
|
82
90
|
end
|
|
83
91
|
end
|
|
84
92
|
end
|
|
@@ -14,14 +14,13 @@ module PubSubModelSync
|
|
|
14
14
|
publish(data, attributes)
|
|
15
15
|
end
|
|
16
16
|
|
|
17
|
-
# @param
|
|
18
|
-
def publish_model(model, action,
|
|
17
|
+
# @param custom_settings (Hash): { attrs: [], as_klass: nil }
|
|
18
|
+
def publish_model(model, action, custom_settings = {})
|
|
19
19
|
return if model.ps_skip_sync?(action)
|
|
20
20
|
|
|
21
|
-
settings
|
|
21
|
+
settings = model.class.ps_publisher(action).merge(custom_settings)
|
|
22
22
|
attributes = build_model_attrs(model, action, settings)
|
|
23
|
-
data =
|
|
24
|
-
data = build_model_data(model, settings[:attrs]) if action != :destroy
|
|
23
|
+
data = build_model_data(model, settings[:attrs])
|
|
25
24
|
res_before = model.ps_before_sync(action, data)
|
|
26
25
|
return if res_before == :cancel
|
|
27
26
|
|
|
@@ -29,12 +28,8 @@ module PubSubModelSync
|
|
|
29
28
|
model.ps_after_sync(action, data)
|
|
30
29
|
end
|
|
31
30
|
|
|
32
|
-
def self.build_attrs(klass, action
|
|
33
|
-
{
|
|
34
|
-
klass: klass.to_s,
|
|
35
|
-
action: action.to_sym,
|
|
36
|
-
id: id
|
|
37
|
-
}
|
|
31
|
+
def self.build_attrs(klass, action)
|
|
32
|
+
{ klass: klass.to_s, action: action.to_sym }
|
|
38
33
|
end
|
|
39
34
|
|
|
40
35
|
private
|
|
@@ -52,8 +47,7 @@ module PubSubModelSync
|
|
|
52
47
|
|
|
53
48
|
def build_model_attrs(model, action, settings)
|
|
54
49
|
as_klass = (settings[:as_klass] || model.class.name).to_s
|
|
55
|
-
|
|
56
|
-
self.class.build_attrs(as_klass, action, id_val)
|
|
50
|
+
self.class.build_attrs(as_klass, action)
|
|
57
51
|
end
|
|
58
52
|
|
|
59
53
|
def log(msg)
|
|
@@ -23,20 +23,20 @@ module PubSubModelSync
|
|
|
23
23
|
def ps_after_sync(_action, _data); end
|
|
24
24
|
|
|
25
25
|
# To perform sync on demand
|
|
26
|
-
# @param custom_settings (Hash): { attrs: [], as_klass: nil
|
|
26
|
+
# @param custom_settings (Hash): { attrs: [], as_klass: nil }
|
|
27
27
|
def ps_perform_sync(action = :create, custom_settings = {})
|
|
28
28
|
service = self.class.ps_publisher_service
|
|
29
|
-
model_settings = self.class.
|
|
29
|
+
model_settings = self.class.ps_publisher(action) || {}
|
|
30
30
|
service.publish_model(self, action, model_settings.merge(custom_settings))
|
|
31
31
|
end
|
|
32
32
|
|
|
33
33
|
module ClassMethods
|
|
34
34
|
# Permit to configure to publish crud actions (:create, :update, :destroy)
|
|
35
|
-
|
|
36
|
-
|
|
37
|
-
actions = settings.delete(:actions) || %i[create update destroy]
|
|
35
|
+
def ps_publish(attrs, actions: %i[create update destroy], as_klass: nil)
|
|
36
|
+
as_klass ||= name
|
|
38
37
|
actions.each do |action|
|
|
39
|
-
info =
|
|
38
|
+
info = { klass: name, action: action, attrs: attrs,
|
|
39
|
+
as_klass: as_klass }
|
|
40
40
|
PubSubModelSync::Config.publishers << info
|
|
41
41
|
ps_register_callback(action.to_sym, info)
|
|
42
42
|
end
|
|
@@ -49,10 +49,10 @@ module PubSubModelSync
|
|
|
49
49
|
end
|
|
50
50
|
|
|
51
51
|
# Publisher info for specific action
|
|
52
|
-
def
|
|
53
|
-
PubSubModelSync::Config.publishers.
|
|
52
|
+
def ps_publisher(action = :create)
|
|
53
|
+
PubSubModelSync::Config.publishers.find do |listener|
|
|
54
54
|
listener[:klass] == name && listener[:action] == action
|
|
55
|
-
end
|
|
55
|
+
end
|
|
56
56
|
end
|
|
57
57
|
|
|
58
58
|
def ps_publisher_service
|
|
@@ -18,11 +18,11 @@ module PubSubModelSync
|
|
|
18
18
|
|
|
19
19
|
private
|
|
20
20
|
|
|
21
|
-
# @param payload (String JSON): '{"data":{},"attributes":{..}}'
|
|
21
|
+
# @param payload (String JSON): '{"data":{}, "attributes":{..}}'
|
|
22
22
|
# refer: PubSubModelSync::Publisher (.publish_model | .publish_data)
|
|
23
23
|
def perform_message(payload)
|
|
24
24
|
data, attrs = parse_message_payload(payload)
|
|
25
|
-
args = [data, attrs[:klass], attrs[:action]
|
|
25
|
+
args = [data, attrs[:klass], attrs[:action]]
|
|
26
26
|
PubSubModelSync::MessageProcessor.new(*args).process
|
|
27
27
|
end
|
|
28
28
|
|
|
@@ -7,11 +7,9 @@ module PubSubModelSync
|
|
|
7
7
|
end
|
|
8
8
|
|
|
9
9
|
module ClassMethods
|
|
10
|
-
|
|
11
|
-
|
|
12
|
-
|
|
13
|
-
actions = settings.delete(:actions) || %i[create update destroy]
|
|
14
|
-
settings = settings.merge(attrs: attrs)
|
|
10
|
+
def ps_subscribe(attrs, as_klass: nil, actions: nil, id: :id)
|
|
11
|
+
actions ||= %i[create update destroy]
|
|
12
|
+
settings = { attrs: attrs, id: id }
|
|
15
13
|
actions.each do |action|
|
|
16
14
|
add_ps_subscriber(as_klass, action, action, false, settings)
|
|
17
15
|
end
|
|
@@ -22,13 +20,14 @@ module PubSubModelSync
|
|
|
22
20
|
end
|
|
23
21
|
|
|
24
22
|
def ps_subscriber(action = :create)
|
|
25
|
-
PubSubModelSync::Config.listeners.
|
|
23
|
+
PubSubModelSync::Config.listeners.find do |listener|
|
|
26
24
|
listener[:klass] == name && listener[:action] == action
|
|
27
|
-
end
|
|
25
|
+
end
|
|
28
26
|
end
|
|
29
27
|
|
|
30
28
|
private
|
|
31
29
|
|
|
30
|
+
# @param settings (Hash): { id:, attrs: }
|
|
32
31
|
def add_ps_subscriber(as_klass, action, as_action, direct_mode, settings)
|
|
33
32
|
listener = {
|
|
34
33
|
klass: name,
|
|
@@ -38,7 +37,7 @@ module PubSubModelSync
|
|
|
38
37
|
direct_mode: direct_mode,
|
|
39
38
|
settings: settings
|
|
40
39
|
}
|
|
41
|
-
PubSubModelSync::Config.listeners
|
|
40
|
+
PubSubModelSync::Config.listeners.push(listener) && listener
|
|
42
41
|
end
|
|
43
42
|
end
|
|
44
43
|
end
|
metadata
CHANGED
|
@@ -1,14 +1,14 @@
|
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
|
2
2
|
name: pub_sub_model_sync
|
|
3
3
|
version: !ruby/object:Gem::Version
|
|
4
|
-
version: 0.
|
|
4
|
+
version: 0.3.0
|
|
5
5
|
platform: ruby
|
|
6
6
|
authors:
|
|
7
7
|
- Owen
|
|
8
8
|
autorequire:
|
|
9
9
|
bindir: exe
|
|
10
10
|
cert_chain: []
|
|
11
|
-
date: 2020-04-
|
|
11
|
+
date: 2020-04-29 00:00:00.000000000 Z
|
|
12
12
|
dependencies:
|
|
13
13
|
- !ruby/object:Gem::Dependency
|
|
14
14
|
name: activesupport
|
|
@@ -103,6 +103,15 @@ extra_rdoc_files: []
|
|
|
103
103
|
files:
|
|
104
104
|
- ".github/workflows/ruby.yml"
|
|
105
105
|
- ".gitignore"
|
|
106
|
+
- ".idea/.gitignore"
|
|
107
|
+
- ".idea/.rakeTasks"
|
|
108
|
+
- ".idea/codeStyles/codeStyleConfig.xml"
|
|
109
|
+
- ".idea/encodings.xml"
|
|
110
|
+
- ".idea/inspectionProfiles/Project_Default.xml"
|
|
111
|
+
- ".idea/misc.xml"
|
|
112
|
+
- ".idea/modules.xml"
|
|
113
|
+
- ".idea/pub_sub_model_sync.iml"
|
|
114
|
+
- ".idea/vcs.xml"
|
|
106
115
|
- ".rspec"
|
|
107
116
|
- ".rubocop.yml"
|
|
108
117
|
- CHANGELOG.md
|