cloudenvoy 0.1.0.dev → 0.4.0

Sign up to get free protection for your applications and to get access to all the features.
Files changed (110) hide show
  1. checksums.yaml +4 -4
  2. data/.github/workflows/test.yml +41 -0
  3. data/.gitignore +3 -0
  4. data/.rubocop.yml +1 -0
  5. data/Appraisals +25 -0
  6. data/CHANGELOG.md +32 -0
  7. data/Gemfile.lock +215 -1
  8. data/README.md +581 -7
  9. data/app/controllers/cloudenvoy/application_controller.rb +8 -0
  10. data/app/controllers/cloudenvoy/subscriber_controller.rb +59 -0
  11. data/cloudenvoy.gemspec +15 -2
  12. data/config/routes.rb +5 -0
  13. data/examples/rails/.ruby-version +1 -0
  14. data/examples/rails/Gemfile +15 -0
  15. data/examples/rails/Gemfile.lock +207 -0
  16. data/examples/rails/Procfile +1 -0
  17. data/examples/rails/README.md +31 -0
  18. data/examples/rails/Rakefile +8 -0
  19. data/examples/rails/app/assets/config/manifest.js +2 -0
  20. data/examples/rails/app/assets/images/.keep +0 -0
  21. data/examples/rails/app/assets/stylesheets/application.css +15 -0
  22. data/examples/rails/app/channels/application_cable/channel.rb +6 -0
  23. data/examples/rails/app/channels/application_cable/connection.rb +6 -0
  24. data/examples/rails/app/controllers/application_controller.rb +4 -0
  25. data/examples/rails/app/controllers/concerns/.keep +0 -0
  26. data/examples/rails/app/helpers/application_helper.rb +4 -0
  27. data/examples/rails/app/javascript/packs/application.js +15 -0
  28. data/examples/rails/app/jobs/application_job.rb +9 -0
  29. data/examples/rails/app/mailers/application_mailer.rb +6 -0
  30. data/examples/rails/app/models/application_record.rb +5 -0
  31. data/examples/rails/app/models/concerns/.keep +0 -0
  32. data/examples/rails/app/publishers/hello_publisher.rb +34 -0
  33. data/examples/rails/app/subscribers/hello_subscriber.rb +16 -0
  34. data/examples/rails/app/views/layouts/application.html.erb +14 -0
  35. data/examples/rails/app/views/layouts/mailer.html.erb +13 -0
  36. data/examples/rails/app/views/layouts/mailer.text.erb +1 -0
  37. data/examples/rails/bin/rails +6 -0
  38. data/examples/rails/bin/rake +6 -0
  39. data/examples/rails/bin/setup +35 -0
  40. data/examples/rails/config.ru +7 -0
  41. data/examples/rails/config/application.rb +19 -0
  42. data/examples/rails/config/boot.rb +7 -0
  43. data/examples/rails/config/cable.yml +10 -0
  44. data/examples/rails/config/credentials.yml.enc +1 -0
  45. data/examples/rails/config/database.yml +25 -0
  46. data/examples/rails/config/environment.rb +7 -0
  47. data/examples/rails/config/environments/development.rb +65 -0
  48. data/examples/rails/config/environments/production.rb +114 -0
  49. data/examples/rails/config/environments/test.rb +50 -0
  50. data/examples/rails/config/initializers/application_controller_renderer.rb +9 -0
  51. data/examples/rails/config/initializers/assets.rb +14 -0
  52. data/examples/rails/config/initializers/backtrace_silencers.rb +8 -0
  53. data/examples/rails/config/initializers/cloudenvoy.rb +22 -0
  54. data/examples/rails/config/initializers/content_security_policy.rb +29 -0
  55. data/examples/rails/config/initializers/cookies_serializer.rb +7 -0
  56. data/examples/rails/config/initializers/filter_parameter_logging.rb +6 -0
  57. data/examples/rails/config/initializers/inflections.rb +17 -0
  58. data/examples/rails/config/initializers/mime_types.rb +5 -0
  59. data/examples/rails/config/initializers/wrap_parameters.rb +16 -0
  60. data/examples/rails/config/locales/en.yml +33 -0
  61. data/examples/rails/config/master.key +1 -0
  62. data/examples/rails/config/puma.rb +37 -0
  63. data/examples/rails/config/routes.rb +4 -0
  64. data/examples/rails/config/spring.rb +8 -0
  65. data/examples/rails/config/storage.yml +34 -0
  66. data/examples/rails/db/development.sqlite3 +0 -0
  67. data/examples/rails/db/test.sqlite3 +0 -0
  68. data/examples/rails/lib/assets/.keep +0 -0
  69. data/examples/rails/log/.keep +0 -0
  70. data/examples/rails/public/404.html +67 -0
  71. data/examples/rails/public/422.html +67 -0
  72. data/examples/rails/public/500.html +66 -0
  73. data/examples/rails/public/apple-touch-icon-precomposed.png +0 -0
  74. data/examples/rails/public/apple-touch-icon.png +0 -0
  75. data/examples/rails/public/favicon.ico +0 -0
  76. data/examples/rails/storage/.keep +0 -0
  77. data/gemfiles/rails_5.2.gemfile +7 -0
  78. data/gemfiles/rails_5.2.gemfile.lock +251 -0
  79. data/gemfiles/rails_6.0.gemfile +7 -0
  80. data/gemfiles/rails_6.0.gemfile.lock +267 -0
  81. data/gemfiles/semantic_logger_3.4.gemfile +7 -0
  82. data/gemfiles/semantic_logger_3.4.gemfile.lock +265 -0
  83. data/gemfiles/semantic_logger_4.6.gemfile +7 -0
  84. data/gemfiles/semantic_logger_4.6.gemfile.lock +265 -0
  85. data/gemfiles/semantic_logger_4.7.0.gemfile +7 -0
  86. data/gemfiles/semantic_logger_4.7.0.gemfile.lock +265 -0
  87. data/gemfiles/semantic_logger_4.7.2.gemfile +7 -0
  88. data/gemfiles/semantic_logger_4.7.2.gemfile.lock +265 -0
  89. data/lib/cloudenvoy.rb +96 -2
  90. data/lib/cloudenvoy/authentication_error.rb +6 -0
  91. data/lib/cloudenvoy/authenticator.rb +57 -0
  92. data/lib/cloudenvoy/backend/google_pub_sub.rb +146 -0
  93. data/lib/cloudenvoy/backend/memory_pub_sub.rb +89 -0
  94. data/lib/cloudenvoy/config.rb +165 -0
  95. data/lib/cloudenvoy/engine.rb +20 -0
  96. data/lib/cloudenvoy/invalid_subscriber_error.rb +6 -0
  97. data/lib/cloudenvoy/logger_wrapper.rb +167 -0
  98. data/lib/cloudenvoy/message.rb +96 -0
  99. data/lib/cloudenvoy/middleware/chain.rb +250 -0
  100. data/lib/cloudenvoy/pub_sub_client.rb +76 -0
  101. data/lib/cloudenvoy/publisher.rb +211 -0
  102. data/lib/cloudenvoy/publisher_logger.rb +32 -0
  103. data/lib/cloudenvoy/subscriber.rb +222 -0
  104. data/lib/cloudenvoy/subscriber_logger.rb +26 -0
  105. data/lib/cloudenvoy/subscription.rb +19 -0
  106. data/lib/cloudenvoy/testing.rb +106 -0
  107. data/lib/cloudenvoy/topic.rb +19 -0
  108. data/lib/cloudenvoy/version.rb +1 -1
  109. data/lib/tasks/cloudenvoy.rake +61 -0
  110. metadata +263 -6
@@ -0,0 +1,8 @@
1
+ # frozen_string_literal: true
2
+
3
+ module Cloudenvoy
4
+ # Base Cloudenvoy controller
5
+ class ApplicationController < ActionController::Base
6
+ skip_before_action :verify_authenticity_token
7
+ end
8
+ end
@@ -0,0 +1,59 @@
1
+ # frozen_string_literal: true
2
+
3
+ module Cloudenvoy
4
+ # Handle execution of Cloudenvoy subscribers
5
+ class SubscriberController < ApplicationController
6
+ # Authenticate all requests.
7
+ before_action :authenticate!
8
+
9
+ # Return 401 when API Token is invalid
10
+ rescue_from AuthenticationError do
11
+ head :unauthorized
12
+ end
13
+
14
+ # POST /cloudenvoy/receive
15
+ #
16
+ # Process a Pub/Sub message using a Cloudenvoy subscriber.
17
+ #
18
+ def receive
19
+ # Process msg_descriptor
20
+ Subscriber.execute_from_descriptor(msg_descriptor)
21
+ head :no_content
22
+ rescue InvalidSubscriberError
23
+ # 404: Message delivery will be retried
24
+ head :not_found
25
+ rescue StandardError => e
26
+ # 422: Message delivery will be retried
27
+ Cloudenvoy.logger.error(e)
28
+ Cloudenvoy.logger.error(e.backtrace.join("\n"))
29
+ head :unprocessable_entity
30
+ end
31
+
32
+ private
33
+
34
+ #
35
+ # Parse the request body and return the actual message
36
+ # descriptor.
37
+ #
38
+ # @return [Hash] The descriptor payload
39
+ #
40
+ def msg_descriptor
41
+ @msg_descriptor ||= begin
42
+ # Get raw body
43
+ content = request.body.read
44
+
45
+ # Return content parsed as JSON and add job retries count
46
+ JSON.parse(content).except('token')
47
+ end
48
+ end
49
+
50
+ #
51
+ # Authenticate incoming requests via a token parameter
52
+ #
53
+ # See Cloudenvoy::Authenticator#verification_token
54
+ #
55
+ def authenticate!
56
+ Authenticator.verify!(params['token'])
57
+ end
58
+ end
59
+ end
@@ -8,8 +8,8 @@ Gem::Specification.new do |spec|
8
8
  spec.authors = ['Arnaud Lachaume']
9
9
  spec.email = ['arnaud.lachaume@keypup.io']
10
10
 
11
- spec.summary = 'Cross-application messaging using GCP Pub/Sub (in development)'
12
- spec.description = 'Cross-application messaging using GCP Pub/Sub (in development)'
11
+ spec.summary = 'Cross-application messaging using GCP Pub/Sub (alpha)'
12
+ spec.description = 'Cross-application messaging using GCP Pub/Sub (alpha)'
13
13
  spec.homepage = 'https://github.com/keypup-io/cloudenvoy'
14
14
  spec.license = 'MIT'
15
15
  spec.required_ruby_version = Gem::Requirement.new('>= 2.3.0')
@@ -27,8 +27,21 @@ Gem::Specification.new do |spec|
27
27
  spec.executables = spec.files.grep(%r{^exe/}) { |f| File.basename(f) }
28
28
  spec.require_paths = ['lib']
29
29
 
30
+ spec.add_dependency 'activesupport'
31
+ spec.add_dependency 'google-cloud-pubsub', '~> 2.0'
32
+ spec.add_dependency 'jwt'
33
+ spec.add_dependency 'retriable'
34
+
35
+ spec.add_development_dependency 'appraisal'
30
36
  spec.add_development_dependency 'rake', '>= 12.3.3'
31
37
  spec.add_development_dependency 'rspec', '~> 3.0'
32
38
  spec.add_development_dependency 'rubocop', '0.76.0'
33
39
  spec.add_development_dependency 'rubocop-rspec', '1.37.0'
40
+ spec.add_development_dependency 'semantic_logger'
41
+ spec.add_development_dependency 'timecop'
42
+ spec.add_development_dependency 'webmock'
43
+
44
+ spec.add_development_dependency 'rails'
45
+ spec.add_development_dependency 'rspec-rails'
46
+ spec.add_development_dependency 'sqlite3'
34
47
  end
@@ -0,0 +1,5 @@
1
+ # frozen_string_literal: true
2
+
3
+ Cloudenvoy::Engine.routes.draw do
4
+ post '/receive', to: 'subscriber#receive'
5
+ end
@@ -0,0 +1 @@
1
+ ruby-2.5.5
@@ -0,0 +1,15 @@
1
+ # frozen_string_literal: true
2
+
3
+ source 'https://rubygems.org'
4
+ git_source(:github) { |repo| "https://github.com/#{repo}.git" }
5
+
6
+ ruby '2.5.5'
7
+
8
+ # Bundle edge Rails instead: gem 'rails', github: 'rails/rails'
9
+ gem 'rails', '~> 6.0.2'
10
+
11
+ # Messaging via GCP Pub/Sub
12
+ gem 'cloudenvoy', path: '../../'
13
+
14
+ # Active record adapter
15
+ gem 'sqlite3'
@@ -0,0 +1,207 @@
1
+ PATH
2
+ remote: ../..
3
+ specs:
4
+ cloudenvoy (0.3.0)
5
+ activesupport
6
+ google-cloud-pubsub (~> 2.0)
7
+ jwt
8
+ retriable
9
+
10
+ GEM
11
+ remote: https://rubygems.org/
12
+ specs:
13
+ actioncable (6.0.3.2)
14
+ actionpack (= 6.0.3.2)
15
+ nio4r (~> 2.0)
16
+ websocket-driver (>= 0.6.1)
17
+ actionmailbox (6.0.3.2)
18
+ actionpack (= 6.0.3.2)
19
+ activejob (= 6.0.3.2)
20
+ activerecord (= 6.0.3.2)
21
+ activestorage (= 6.0.3.2)
22
+ activesupport (= 6.0.3.2)
23
+ mail (>= 2.7.1)
24
+ actionmailer (6.0.3.2)
25
+ actionpack (= 6.0.3.2)
26
+ actionview (= 6.0.3.2)
27
+ activejob (= 6.0.3.2)
28
+ mail (~> 2.5, >= 2.5.4)
29
+ rails-dom-testing (~> 2.0)
30
+ actionpack (6.0.3.2)
31
+ actionview (= 6.0.3.2)
32
+ activesupport (= 6.0.3.2)
33
+ rack (~> 2.0, >= 2.0.8)
34
+ rack-test (>= 0.6.3)
35
+ rails-dom-testing (~> 2.0)
36
+ rails-html-sanitizer (~> 1.0, >= 1.2.0)
37
+ actiontext (6.0.3.2)
38
+ actionpack (= 6.0.3.2)
39
+ activerecord (= 6.0.3.2)
40
+ activestorage (= 6.0.3.2)
41
+ activesupport (= 6.0.3.2)
42
+ nokogiri (>= 1.8.5)
43
+ actionview (6.0.3.2)
44
+ activesupport (= 6.0.3.2)
45
+ builder (~> 3.1)
46
+ erubi (~> 1.4)
47
+ rails-dom-testing (~> 2.0)
48
+ rails-html-sanitizer (~> 1.1, >= 1.2.0)
49
+ activejob (6.0.3.2)
50
+ activesupport (= 6.0.3.2)
51
+ globalid (>= 0.3.6)
52
+ activemodel (6.0.3.2)
53
+ activesupport (= 6.0.3.2)
54
+ activerecord (6.0.3.2)
55
+ activemodel (= 6.0.3.2)
56
+ activesupport (= 6.0.3.2)
57
+ activestorage (6.0.3.2)
58
+ actionpack (= 6.0.3.2)
59
+ activejob (= 6.0.3.2)
60
+ activerecord (= 6.0.3.2)
61
+ marcel (~> 0.3.1)
62
+ activesupport (6.0.3.2)
63
+ concurrent-ruby (~> 1.0, >= 1.0.2)
64
+ i18n (>= 0.7, < 2)
65
+ minitest (~> 5.1)
66
+ tzinfo (~> 1.1)
67
+ zeitwerk (~> 2.2, >= 2.2.2)
68
+ addressable (2.7.0)
69
+ public_suffix (>= 2.0.2, < 5.0)
70
+ builder (3.2.4)
71
+ concurrent-ruby (1.1.7)
72
+ crass (1.0.6)
73
+ erubi (1.9.0)
74
+ faraday (1.0.1)
75
+ multipart-post (>= 1.2, < 3)
76
+ gapic-common (0.3.4)
77
+ google-protobuf (~> 3.12, >= 3.12.2)
78
+ googleapis-common-protos (>= 1.3.9, < 2.0)
79
+ googleapis-common-protos-types (>= 1.0.4, < 2.0)
80
+ googleauth (~> 0.9)
81
+ grpc (~> 1.25)
82
+ globalid (0.4.2)
83
+ activesupport (>= 4.2.0)
84
+ google-cloud-core (1.5.0)
85
+ google-cloud-env (~> 1.0)
86
+ google-cloud-errors (~> 1.0)
87
+ google-cloud-env (1.3.3)
88
+ faraday (>= 0.17.3, < 2.0)
89
+ google-cloud-errors (1.0.1)
90
+ google-cloud-pubsub (2.0.0)
91
+ concurrent-ruby (~> 1.1)
92
+ google-cloud-core (~> 1.5)
93
+ google-cloud-pubsub-v1 (~> 0.0)
94
+ google-cloud-pubsub-v1 (0.1.2)
95
+ gapic-common (~> 0.3)
96
+ google-cloud-errors (~> 1.0)
97
+ grpc-google-iam-v1 (>= 0.6.10, < 2.0)
98
+ google-protobuf (3.13.0-universal-darwin)
99
+ googleapis-common-protos (1.3.10)
100
+ google-protobuf (~> 3.11)
101
+ googleapis-common-protos-types (>= 1.0.5, < 2.0)
102
+ grpc (~> 1.27)
103
+ googleapis-common-protos-types (1.0.5)
104
+ google-protobuf (~> 3.11)
105
+ googleauth (0.13.1)
106
+ faraday (>= 0.17.3, < 2.0)
107
+ jwt (>= 1.4, < 3.0)
108
+ memoist (~> 0.16)
109
+ multi_json (~> 1.11)
110
+ os (>= 0.9, < 2.0)
111
+ signet (~> 0.14)
112
+ grpc (1.32.0-universal-darwin)
113
+ google-protobuf (~> 3.13)
114
+ googleapis-common-protos-types (~> 1.0)
115
+ grpc-google-iam-v1 (0.6.10)
116
+ google-protobuf (~> 3.11)
117
+ googleapis-common-protos (>= 1.3.10, < 2.0)
118
+ grpc (~> 1.27)
119
+ i18n (1.8.5)
120
+ concurrent-ruby (~> 1.0)
121
+ jwt (2.2.2)
122
+ loofah (2.6.0)
123
+ crass (~> 1.0.2)
124
+ nokogiri (>= 1.5.9)
125
+ mail (2.7.1)
126
+ mini_mime (>= 0.1.1)
127
+ marcel (0.3.3)
128
+ mimemagic (~> 0.3.2)
129
+ memoist (0.16.2)
130
+ method_source (1.0.0)
131
+ mimemagic (0.3.5)
132
+ mini_mime (1.0.2)
133
+ mini_portile2 (2.4.0)
134
+ minitest (5.14.2)
135
+ multi_json (1.15.0)
136
+ multipart-post (2.1.1)
137
+ nio4r (2.5.2)
138
+ nokogiri (1.10.9)
139
+ mini_portile2 (~> 2.4.0)
140
+ os (1.1.1)
141
+ public_suffix (4.0.6)
142
+ rack (2.2.3)
143
+ rack-test (1.1.0)
144
+ rack (>= 1.0, < 3)
145
+ rails (6.0.3.2)
146
+ actioncable (= 6.0.3.2)
147
+ actionmailbox (= 6.0.3.2)
148
+ actionmailer (= 6.0.3.2)
149
+ actionpack (= 6.0.3.2)
150
+ actiontext (= 6.0.3.2)
151
+ actionview (= 6.0.3.2)
152
+ activejob (= 6.0.3.2)
153
+ activemodel (= 6.0.3.2)
154
+ activerecord (= 6.0.3.2)
155
+ activestorage (= 6.0.3.2)
156
+ activesupport (= 6.0.3.2)
157
+ bundler (>= 1.3.0)
158
+ railties (= 6.0.3.2)
159
+ sprockets-rails (>= 2.0.0)
160
+ rails-dom-testing (2.0.3)
161
+ activesupport (>= 4.2.0)
162
+ nokogiri (>= 1.6)
163
+ rails-html-sanitizer (1.3.0)
164
+ loofah (~> 2.3)
165
+ railties (6.0.3.2)
166
+ actionpack (= 6.0.3.2)
167
+ activesupport (= 6.0.3.2)
168
+ method_source
169
+ rake (>= 0.8.7)
170
+ thor (>= 0.20.3, < 2.0)
171
+ rake (13.0.1)
172
+ retriable (3.1.2)
173
+ signet (0.14.0)
174
+ addressable (~> 2.3)
175
+ faraday (>= 0.17.3, < 2.0)
176
+ jwt (>= 1.5, < 3.0)
177
+ multi_json (~> 1.10)
178
+ sprockets (4.0.2)
179
+ concurrent-ruby (~> 1.0)
180
+ rack (> 1, < 3)
181
+ sprockets-rails (3.2.1)
182
+ actionpack (>= 4.0)
183
+ activesupport (>= 4.0)
184
+ sprockets (>= 3.0.0)
185
+ sqlite3 (1.4.2)
186
+ thor (1.0.1)
187
+ thread_safe (0.3.6)
188
+ tzinfo (1.2.7)
189
+ thread_safe (~> 0.1)
190
+ websocket-driver (0.7.2)
191
+ websocket-extensions (>= 0.1.0)
192
+ websocket-extensions (0.1.5)
193
+ zeitwerk (2.4.0)
194
+
195
+ PLATFORMS
196
+ ruby
197
+
198
+ DEPENDENCIES
199
+ cloudenvoy!
200
+ rails (~> 6.0.2)
201
+ sqlite3
202
+
203
+ RUBY VERSION
204
+ ruby 2.5.5p157
205
+
206
+ BUNDLED WITH
207
+ 2.1.4
@@ -0,0 +1 @@
1
+ web: bundle exec rake cloudenvoy:setup && bundle exec rails s -p 3000
@@ -0,0 +1,31 @@
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: `rails c`
10
+ 6. Publish messages:
11
+ ```ruby
12
+ HelloPublisher.publish('Some message')
13
+ ```
14
+ 7. Tail the logs to see how message get processed by `HelloSubscriber`
15
+
16
+ ## Run using GCP Pub/Sub
17
+
18
+ 1. Ensure that your [Google Cloud SDK](https://cloud.google.com/sdk/docs/quickstarts) is setup.
19
+ 2. Install dependencies: `bundle install`
20
+ 3. Start an [ngrok](https://ngrok.com) tunnel: `ngrok http 3000`
21
+ 4. Edit the [initializer](./config/initializers/cloudenvoy.rb)
22
+ * Add the configuration of your GCP Pub/Sub
23
+ * Set `config.processor_host` to the ngrok http or https url
24
+ * Set `config.mode` to `:production`
25
+ 5. Launch the server: `foreman start web`
26
+ 6. Open a Rails console: `rails c`
27
+ 7. Publish messages
28
+ ```ruby
29
+ HelloPublisher.publish('Some message')
30
+ ```
31
+ 8. Tail the logs to see how message get processed by `HelloSubscriber`
@@ -0,0 +1,8 @@
1
+ # frozen_string_literal: true
2
+
3
+ # Add your own tasks in files placed in lib/tasks ending in .rake,
4
+ # for example lib/tasks/capistrano.rake, and they will automatically be available to Rake.
5
+
6
+ require_relative 'config/application'
7
+
8
+ Rails.application.load_tasks
@@ -0,0 +1,2 @@
1
+ //= link_tree ../images
2
+ //= link_directory ../stylesheets .css
File without changes
@@ -0,0 +1,15 @@
1
+ /*
2
+ * This is a manifest file that'll be compiled into application.css, which will include all the files
3
+ * listed below.
4
+ *
5
+ * Any CSS and SCSS file within this directory, lib/assets/stylesheets, vendor/assets/stylesheets,
6
+ * or any plugin's vendor/assets/stylesheets directory can be referenced here using a relative path.
7
+ *
8
+ * You're free to add application-wide styles to this file and they'll appear at the bottom of the
9
+ * compiled file so the styles you add here take precedence over styles defined in any other CSS/SCSS
10
+ * files in this directory. Styles in this file should be added after the last require_* statement.
11
+ * It is generally better to create a new file per style scope.
12
+ *
13
+ *= require_tree .
14
+ *= require_self
15
+ */
@@ -0,0 +1,6 @@
1
+ # frozen_string_literal: true
2
+
3
+ module ApplicationCable
4
+ class Channel < ActionCable::Channel::Base
5
+ end
6
+ end
@@ -0,0 +1,6 @@
1
+ # frozen_string_literal: true
2
+
3
+ module ApplicationCable
4
+ class Connection < ActionCable::Connection::Base
5
+ end
6
+ end
@@ -0,0 +1,4 @@
1
+ # frozen_string_literal: true
2
+
3
+ class ApplicationController < ActionController::Base
4
+ end
@@ -0,0 +1,4 @@
1
+ # frozen_string_literal: true
2
+
3
+ module ApplicationHelper
4
+ end
@@ -0,0 +1,15 @@
1
+ // This is a manifest file that'll be compiled into application.js, which will include all the files
2
+ // listed below.
3
+ //
4
+ // Any JavaScript/Coffee file within this directory, lib/assets/javascripts, vendor/assets/javascripts,
5
+ // or any plugin's vendor/assets/javascripts directory can be referenced here using a relative path.
6
+ //
7
+ // It's not advisable to add code directly here, but if you do, it'll appear at the bottom of the
8
+ // compiled file. JavaScript code in this file should be added after the last require_* statement.
9
+ //
10
+ // Read Sprockets README (https://github.com/rails/sprockets#sprockets-directives) for details
11
+ // about supported directives.
12
+ //
13
+ //= require rails-ujs
14
+ //= require activestorage
15
+ //= require_tree .