cloudenvoy 0.3.0 → 0.4.2

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.
Files changed (44) hide show
  1. checksums.yaml +4 -4
  2. data/.github/workflows/test.yml +4 -0
  3. data/.gitignore +3 -0
  4. data/Appraisals +16 -0
  5. data/CHANGELOG.md +29 -0
  6. data/README.md +4 -4
  7. data/app/controllers/cloudenvoy/subscriber_controller.rb +6 -5
  8. data/cloudenvoy.gemspec +1 -0
  9. data/examples/rails/Gemfile.lock +125 -106
  10. data/examples/sinatra/Gemfile +15 -0
  11. data/examples/sinatra/Gemfile.lock +127 -0
  12. data/examples/sinatra/Procfile +1 -0
  13. data/examples/sinatra/README.md +41 -0
  14. data/examples/sinatra/app/publishers/hello_publisher.rb +34 -0
  15. data/examples/sinatra/app/subscribers/hello_subscriber.rb +16 -0
  16. data/examples/sinatra/app.rb +40 -0
  17. data/examples/sinatra/bin/console +8 -0
  18. data/examples/sinatra/config/initializers/cloudenvoy.rb +30 -0
  19. data/gemfiles/rails_5.2.gemfile.lock +89 -73
  20. data/gemfiles/rails_6.0.gemfile.lock +90 -74
  21. data/gemfiles/semantic_logger_3.4.gemfile +7 -0
  22. data/gemfiles/semantic_logger_3.4.gemfile.lock +279 -0
  23. data/gemfiles/semantic_logger_4.6.gemfile +7 -0
  24. data/gemfiles/semantic_logger_4.6.gemfile.lock +279 -0
  25. data/gemfiles/semantic_logger_4.7.0.gemfile +7 -0
  26. data/gemfiles/semantic_logger_4.7.0.gemfile.lock +279 -0
  27. data/gemfiles/semantic_logger_4.7.2.gemfile +7 -0
  28. data/gemfiles/semantic_logger_4.7.2.gemfile.lock +279 -0
  29. data/lib/cloudenvoy/backend/google_pub_sub.rb +16 -1
  30. data/lib/cloudenvoy/logger_wrapper.rb +1 -1
  31. data/lib/cloudenvoy/message.rb +2 -2
  32. data/lib/cloudenvoy/publisher.rb +1 -0
  33. data/lib/cloudenvoy/subscriber.rb +3 -2
  34. data/lib/cloudenvoy/version.rb +1 -1
  35. data/lib/generators/cloudenvoy/publisher_generator.rb +46 -0
  36. data/lib/generators/cloudenvoy/subscriber_generator.rb +46 -0
  37. data/lib/generators/cloudenvoy/templates/publisher.rb.erb +11 -0
  38. data/lib/generators/cloudenvoy/templates/publisher_spec.rb.erb +6 -0
  39. data/lib/generators/cloudenvoy/templates/subscriber.rb.erb +11 -0
  40. data/lib/generators/cloudenvoy/templates/subscriber_spec.rb.erb +6 -0
  41. data/lib/tasks/cloudenvoy.rake +4 -4
  42. metadata +42 -7
  43. data/Gemfile.lock +0 -264
  44. data/app/controllers/cloudenvoy/application_controller.rb +0 -8
@@ -0,0 +1,41 @@
1
+ # Example usage with Rails
2
+
3
+ ## Run using the local gcloud Pub/Sub emulator
4
+
5
+ 1. Install dependencies: `bundle install`
6
+ 2. Intall the Pub/Sub emulator: `gcloud components install pubsub-emulator && gcloud components update`
7
+ 3. Run the Pub/Sub emulator: `gcloud beta emulators pubsub start`
8
+ 4. Launch the server: `foreman start`
9
+ 5. Open a Rails console: `./bin/console`
10
+ 6. Create the topics and subscriptions (one time setup - no need to redo it until you restart the pubsub emulator)
11
+ ```ruby
12
+ Cloudenvoy.setup_publishers
13
+ Cloudenvoy.setup_subscribers
14
+ ```
15
+ 7. Publish messages:
16
+ ```ruby
17
+ HelloPublisher.publish('Some message')
18
+ ```
19
+ 8. Tail the logs to see how message get processed by `HelloSubscriber`
20
+
21
+ ## Run using GCP Pub/Sub
22
+
23
+ 1. Ensure that your [Google Cloud SDK](https://cloud.google.com/sdk/docs/quickstarts) is setup.
24
+ 2. Install dependencies: `bundle install`
25
+ 3. Start an [ngrok](https://ngrok.com) tunnel: `ngrok http 3000`
26
+ 4. Edit the [initializer](./config/initializers/cloudenvoy.rb)
27
+ * Add the configuration of your GCP Pub/Sub
28
+ * Set `config.processor_host` to the ngrok http or https url
29
+ * Set `config.mode` to `:production`
30
+ 5. Launch the server: `foreman start`
31
+ 6. Open a Rails console: `./bin/console`
32
+ 7. Create the topics and subscriptions (one time setup)
33
+ ```ruby
34
+ Cloudenvoy.setup_publishers
35
+ Cloudenvoy.setup_subscribers
36
+ ```
37
+ 8. Publish messages
38
+ ```ruby
39
+ HelloPublisher.publish('Some message')
40
+ ```
41
+ 9. Tail the logs to see how message get processed by `HelloSubscriber`
@@ -0,0 +1,34 @@
1
+ # frozen_string_literal: true
2
+
3
+ class HelloPublisher
4
+ include Cloudenvoy::Publisher
5
+
6
+ cloudenvoy_options topic: 'hello-msgs'
7
+
8
+ #
9
+ # Set message metadata (attributes)
10
+ #
11
+ # @param [String] msg The message to publish
12
+ #
13
+ # @return [Hash] The message metadata
14
+ #
15
+ def metadata(msg)
16
+ {
17
+ kind: msg.start_with?('Hello') ? 'hello' : 'regular'
18
+ }
19
+ end
20
+
21
+ #
22
+ # Format the payload.
23
+ #
24
+ # @param [String] msg The message to publish
25
+ #
26
+ # @return [Hash] The formatted message
27
+ #
28
+ def payload(msg)
29
+ {
30
+ type: 'message',
31
+ content: msg
32
+ }
33
+ end
34
+ end
@@ -0,0 +1,16 @@
1
+ # frozen_string_literal: true
2
+
3
+ class HelloSubscriber
4
+ include Cloudenvoy::Subscriber
5
+
6
+ cloudenvoy_options topic: 'hello-msgs'
7
+
8
+ #
9
+ # Process a pub/sub message
10
+ #
11
+ # @param [Cloudenvoy::Message] message The message to process.
12
+ #
13
+ def process(message)
14
+ logger.info("Received message #{message.payload.dig('content')}")
15
+ end
16
+ end
@@ -0,0 +1,40 @@
1
+ # frozen_string_literal: true
2
+
3
+ # Force logging to be realtime
4
+ STDOUT.sync = true
5
+
6
+ # Require project files
7
+ require 'sinatra'
8
+ Dir.glob('./config/initializers/*.rb').each { |file| require file }
9
+ Dir.glob('./app/publishers/*.rb').each { |file| require file }
10
+ Dir.glob('./app/subscribers/*.rb').each { |file| require file }
11
+
12
+ #---------------------------------------------------
13
+ # Routes
14
+ #---------------------------------------------------
15
+
16
+ get '/' do
17
+ 'Hello!'
18
+ end
19
+
20
+ post '/cloudenvoy/receive' do
21
+ begin
22
+ # Authenticate request
23
+ Cloudenvoy::Authenticator.verify!(params['token'])
24
+
25
+ # Parse message descriptor
26
+ content = request.body.read
27
+ msg_descriptor = JSON.parse(content).except('token')
28
+
29
+ # Process message descriptor
30
+ Cloudenvoy::Subscriber.execute_from_descriptor(msg_descriptor)
31
+ return 204
32
+ rescue Cloudenvoy::InvalidSubscriberError
33
+ # 404: Message delivery will be retried
34
+ return 404
35
+ rescue StandardError => e
36
+ # 422: Message delivery will be retried
37
+ logger.info([e.message, e.backtrace].flatten.join("\n"))
38
+ return 422
39
+ end
40
+ end
@@ -0,0 +1,8 @@
1
+ #!/usr/bin/env ruby
2
+ # frozen_string_literal: true
3
+
4
+ require 'bundler/setup'
5
+ require File.expand_path('../app.rb', __dir__)
6
+
7
+ require 'irb'
8
+ IRB.start(__FILE__)
@@ -0,0 +1,30 @@
1
+ # frozen_string_literal: true
2
+
3
+ # Require cloudenvoy and its extensions
4
+ require 'cloudenvoy'
5
+
6
+ Cloudenvoy.configure do |config|
7
+ #
8
+ # Secret used to authenticate job requests
9
+ #
10
+ config.secret = 'some-secret'
11
+
12
+ #
13
+ # GCP Configuration
14
+ #
15
+ config.gcp_project_id = 'some-project'
16
+ config.gcp_sub_prefix = 'my-app'
17
+
18
+ #
19
+ # Domain
20
+ #
21
+ # config.processor_host = 'https://xxxx.ngrok.io'
22
+ #
23
+ config.processor_host = 'http://localhost:3000'
24
+
25
+ #
26
+ # Uncomment to process messages via Pub/Sub.
27
+ # Requires a ngrok tunnel.
28
+ #
29
+ # config.mode = :production
30
+ end
@@ -1,7 +1,7 @@
1
1
  PATH
2
2
  remote: ..
3
3
  specs:
4
- cloudenvoy (0.2.0)
4
+ cloudenvoy (0.4.1)
5
5
  activesupport
6
6
  google-cloud-pubsub (~> 2.0)
7
7
  jwt
@@ -53,70 +53,78 @@ GEM
53
53
  tzinfo (~> 1.1)
54
54
  addressable (2.7.0)
55
55
  public_suffix (>= 2.0.2, < 5.0)
56
- appraisal (2.3.0)
56
+ appraisal (2.4.0)
57
57
  bundler
58
58
  rake
59
59
  thor (>= 0.14.0)
60
60
  arel (9.0.0)
61
- ast (2.4.1)
61
+ ast (2.4.2)
62
62
  builder (3.2.4)
63
- concurrent-ruby (1.1.6)
64
- crack (0.4.3)
65
- safe_yaml (~> 1.0.0)
63
+ concurrent-ruby (1.1.8)
64
+ crack (0.4.5)
65
+ rexml
66
66
  crass (1.0.6)
67
- diff-lcs (1.4.2)
68
- erubi (1.9.0)
69
- faraday (1.0.1)
67
+ diff-lcs (1.4.4)
68
+ erubi (1.10.0)
69
+ faraday (1.4.1)
70
+ faraday-excon (~> 1.1)
71
+ faraday-net_http (~> 1.0)
72
+ faraday-net_http_persistent (~> 1.1)
70
73
  multipart-post (>= 1.2, < 3)
71
- gapic-common (0.3.4)
72
- google-protobuf (~> 3.12, >= 3.12.2)
73
- googleapis-common-protos (>= 1.3.9, < 2.0)
74
- googleapis-common-protos-types (>= 1.0.4, < 2.0)
75
- googleauth (~> 0.9)
76
- grpc (~> 1.25)
74
+ ruby2_keywords (>= 0.0.4)
75
+ faraday-excon (1.1.0)
76
+ faraday-net_http (1.0.1)
77
+ faraday-net_http_persistent (1.1.0)
78
+ gapic-common (0.4.1)
79
+ faraday (~> 1.3)
80
+ google-protobuf (~> 3.15, >= 3.15.2)
81
+ googleapis-common-protos (>= 1.3.11, < 2.0)
82
+ googleapis-common-protos-types (>= 1.0.6, < 2.0)
83
+ googleauth (~> 0.15, >= 0.15.1)
84
+ grpc (~> 1.36)
77
85
  globalid (0.4.2)
78
86
  activesupport (>= 4.2.0)
79
- google-cloud-core (1.5.0)
87
+ google-cloud-core (1.6.0)
80
88
  google-cloud-env (~> 1.0)
81
89
  google-cloud-errors (~> 1.0)
82
- google-cloud-env (1.3.3)
90
+ google-cloud-env (1.5.0)
83
91
  faraday (>= 0.17.3, < 2.0)
84
- google-cloud-errors (1.0.1)
85
- google-cloud-pubsub (2.0.0)
92
+ google-cloud-errors (1.1.0)
93
+ google-cloud-pubsub (2.5.0)
86
94
  concurrent-ruby (~> 1.1)
87
95
  google-cloud-core (~> 1.5)
88
96
  google-cloud-pubsub-v1 (~> 0.0)
89
- google-cloud-pubsub-v1 (0.1.2)
97
+ google-cloud-pubsub-v1 (0.4.0)
90
98
  gapic-common (~> 0.3)
91
99
  google-cloud-errors (~> 1.0)
92
100
  grpc-google-iam-v1 (>= 0.6.10, < 2.0)
93
- google-protobuf (3.13.0-universal-darwin)
94
- googleapis-common-protos (1.3.10)
95
- google-protobuf (~> 3.11)
96
- googleapis-common-protos-types (>= 1.0.5, < 2.0)
101
+ google-protobuf (3.15.8)
102
+ googleapis-common-protos (1.3.11)
103
+ google-protobuf (~> 3.14)
104
+ googleapis-common-protos-types (>= 1.0.6, < 2.0)
97
105
  grpc (~> 1.27)
98
- googleapis-common-protos-types (1.0.5)
99
- google-protobuf (~> 3.11)
100
- googleauth (0.13.1)
106
+ googleapis-common-protos-types (1.0.6)
107
+ google-protobuf (~> 3.14)
108
+ googleauth (0.16.1)
101
109
  faraday (>= 0.17.3, < 2.0)
102
110
  jwt (>= 1.4, < 3.0)
103
111
  memoist (~> 0.16)
104
112
  multi_json (~> 1.11)
105
113
  os (>= 0.9, < 2.0)
106
114
  signet (~> 0.14)
107
- grpc (1.32.0-universal-darwin)
108
- google-protobuf (~> 3.13)
115
+ grpc (1.37.0)
116
+ google-protobuf (~> 3.15)
109
117
  googleapis-common-protos-types (~> 1.0)
110
- grpc-google-iam-v1 (0.6.10)
111
- google-protobuf (~> 3.11)
112
- googleapis-common-protos (>= 1.3.10, < 2.0)
118
+ grpc-google-iam-v1 (0.6.11)
119
+ google-protobuf (~> 3.14)
120
+ googleapis-common-protos (>= 1.3.11, < 2.0)
113
121
  grpc (~> 1.27)
114
122
  hashdiff (1.0.1)
115
- i18n (1.8.5)
123
+ i18n (1.8.10)
116
124
  concurrent-ruby (~> 1.0)
117
125
  jaro_winkler (1.5.4)
118
126
  jwt (2.2.2)
119
- loofah (2.6.0)
127
+ loofah (2.9.1)
120
128
  crass (~> 1.0.2)
121
129
  nokogiri (>= 1.5.9)
122
130
  mail (2.7.1)
@@ -125,20 +133,24 @@ GEM
125
133
  mimemagic (~> 0.3.2)
126
134
  memoist (0.16.2)
127
135
  method_source (1.0.0)
128
- mimemagic (0.3.5)
129
- mini_mime (1.0.2)
130
- mini_portile2 (2.4.0)
131
- minitest (5.14.1)
136
+ mimemagic (0.3.10)
137
+ nokogiri (~> 1)
138
+ rake
139
+ mini_mime (1.1.0)
140
+ mini_portile2 (2.5.0)
141
+ minitest (5.14.4)
132
142
  multi_json (1.15.0)
133
143
  multipart-post (2.1.1)
134
- nio4r (2.5.2)
135
- nokogiri (1.10.10)
136
- mini_portile2 (~> 2.4.0)
144
+ nio4r (2.5.7)
145
+ nokogiri (1.11.3)
146
+ mini_portile2 (~> 2.5.0)
147
+ racc (~> 1.4)
137
148
  os (1.1.1)
138
- parallel (1.19.2)
139
- parser (2.7.1.4)
149
+ parallel (1.20.1)
150
+ parser (3.0.1.0)
140
151
  ast (~> 2.4.1)
141
- public_suffix (4.0.5)
152
+ public_suffix (4.0.6)
153
+ racc (1.5.2)
142
154
  rack (2.2.3)
143
155
  rack-test (1.1.0)
144
156
  rack (>= 1.0, < 3)
@@ -167,29 +179,30 @@ GEM
167
179
  rake (>= 0.8.7)
168
180
  thor (>= 0.18.1, < 2.0)
169
181
  rainbow (3.0.0)
170
- rake (13.0.1)
182
+ rake (13.0.3)
171
183
  retriable (3.1.2)
172
- rspec (3.9.0)
173
- rspec-core (~> 3.9.0)
174
- rspec-expectations (~> 3.9.0)
175
- rspec-mocks (~> 3.9.0)
176
- rspec-core (3.9.2)
177
- rspec-support (~> 3.9.3)
178
- rspec-expectations (3.9.2)
184
+ rexml (3.2.5)
185
+ rspec (3.10.0)
186
+ rspec-core (~> 3.10.0)
187
+ rspec-expectations (~> 3.10.0)
188
+ rspec-mocks (~> 3.10.0)
189
+ rspec-core (3.10.1)
190
+ rspec-support (~> 3.10.0)
191
+ rspec-expectations (3.10.1)
179
192
  diff-lcs (>= 1.2.0, < 2.0)
180
- rspec-support (~> 3.9.0)
181
- rspec-mocks (3.9.1)
193
+ rspec-support (~> 3.10.0)
194
+ rspec-mocks (3.10.2)
182
195
  diff-lcs (>= 1.2.0, < 2.0)
183
- rspec-support (~> 3.9.0)
184
- rspec-rails (4.0.1)
185
- actionpack (>= 4.2)
186
- activesupport (>= 4.2)
187
- railties (>= 4.2)
188
- rspec-core (~> 3.9)
189
- rspec-expectations (~> 3.9)
190
- rspec-mocks (~> 3.9)
191
- rspec-support (~> 3.9)
192
- rspec-support (3.9.3)
196
+ rspec-support (~> 3.10.0)
197
+ rspec-rails (5.0.1)
198
+ actionpack (>= 5.2)
199
+ activesupport (>= 5.2)
200
+ railties (>= 5.2)
201
+ rspec-core (~> 3.10)
202
+ rspec-expectations (~> 3.10)
203
+ rspec-mocks (~> 3.10)
204
+ rspec-support (~> 3.10)
205
+ rspec-support (3.10.2)
193
206
  rubocop (0.76.0)
194
207
  jaro_winkler (~> 1.5.1)
195
208
  parallel (~> 1.10)
@@ -199,9 +212,11 @@ GEM
199
212
  unicode-display_width (>= 1.4.0, < 1.7)
200
213
  rubocop-rspec (1.37.0)
201
214
  rubocop (>= 0.68.1)
202
- ruby-progressbar (1.10.1)
203
- safe_yaml (1.0.5)
204
- signet (0.14.0)
215
+ ruby-progressbar (1.11.0)
216
+ ruby2_keywords (0.0.4)
217
+ semantic_logger (4.7.4)
218
+ concurrent-ruby (~> 1.0)
219
+ signet (0.15.0)
205
220
  addressable (~> 2.3)
206
221
  faraday (>= 0.17.3, < 2.0)
207
222
  jwt (>= 1.5, < 3.0)
@@ -209,18 +224,18 @@ GEM
209
224
  sprockets (4.0.2)
210
225
  concurrent-ruby (~> 1.0)
211
226
  rack (> 1, < 3)
212
- sprockets-rails (3.2.1)
227
+ sprockets-rails (3.2.2)
213
228
  actionpack (>= 4.0)
214
229
  activesupport (>= 4.0)
215
230
  sprockets (>= 3.0.0)
216
231
  sqlite3 (1.4.2)
217
- thor (1.0.1)
232
+ thor (1.1.0)
218
233
  thread_safe (0.3.6)
219
- timecop (0.9.1)
220
- tzinfo (1.2.7)
234
+ timecop (0.9.4)
235
+ tzinfo (1.2.9)
221
236
  thread_safe (~> 0.1)
222
237
  unicode-display_width (1.6.1)
223
- webmock (3.8.3)
238
+ webmock (3.12.2)
224
239
  addressable (>= 2.3.6)
225
240
  crack (>= 0.3.2)
226
241
  hashdiff (>= 0.4.0, < 2.0.0)
@@ -240,9 +255,10 @@ DEPENDENCIES
240
255
  rspec-rails
241
256
  rubocop (= 0.76.0)
242
257
  rubocop-rspec (= 1.37.0)
258
+ semantic_logger
243
259
  sqlite3
244
260
  timecop
245
261
  webmock
246
262
 
247
263
  BUNDLED WITH
248
- 2.1.4
264
+ 2.2.9