hephaestus 0.1.3 → 0.2.2

Sign up to get free protection for your applications and to get access to all the features.
Files changed (85) hide show
  1. checksums.yaml +4 -4
  2. data/CHANGELOG.md +4 -0
  3. data/README.md +27 -1
  4. data/bin/hephaestus +9 -3
  5. data/lib/hephaestus/app_builder.rb +26 -5
  6. data/lib/hephaestus/exit_on_failure.rb +4 -4
  7. data/lib/hephaestus/generators/app_generator.rb +148 -56
  8. data/lib/hephaestus/generators/config_generator.rb +30 -2
  9. data/lib/hephaestus/generators/core_generator.rb +30 -1
  10. data/lib/hephaestus/generators/deployment_generator.rb +9 -3
  11. data/lib/hephaestus/generators/lib_generator.rb +1 -0
  12. data/lib/hephaestus/generators/sorbet_generator.rb +1 -1
  13. data/lib/hephaestus/version.rb +1 -1
  14. data/lib/hephaestus.rb +8 -0
  15. data/templates/.dockerignore +39 -0
  16. data/templates/.env.sample +6 -0
  17. data/templates/.github/dependabot.yml +12 -7
  18. data/templates/.github/workflows/automerge.yml +5 -85
  19. data/templates/.github/workflows/deploy.yml +30 -0
  20. data/templates/.github/workflows/licenses.yml +11 -31
  21. data/templates/.github/workflows/lint.yml +14 -34
  22. data/templates/.github/workflows/security.yml +9 -32
  23. data/templates/.github/workflows/sorbet.yml +7 -37
  24. data/templates/.github/workflows/test.yml +7 -41
  25. data/templates/.licensed.yml +7 -3
  26. data/templates/.ruby-version +1 -0
  27. data/templates/Dockerfile +79 -0
  28. data/templates/Gemfile.erb +23 -26
  29. data/templates/Procfile.debug +1 -1
  30. data/templates/app/controllers/app_controller.rb +71 -0
  31. data/templates/app/controllers/application_controller.rb +14 -1
  32. data/templates/app/controllers/concerns/authable.rb +20 -2
  33. data/templates/app/controllers/settings_controller.rb +32 -2
  34. data/templates/app/jobs/update_yetto_job.rb +6 -7
  35. data/templates/app/lib/body_parameter/yetto_parameters.rb +32 -0
  36. data/templates/app/lib/path_parameter/settings_parameters.rb +22 -0
  37. data/templates/app/lib/plug_app/middleware/openapi_validation.rb +5 -5
  38. data/templates/app/lib/plug_app/middleware/tracing_attributes.rb +1 -1
  39. data/templates/app/services/http_service.rb +27 -0
  40. data/templates/app/services/yetto_service.rb +24 -32
  41. data/templates/app/views/settings/new.json.jbuilder +21 -0
  42. data/templates/bin/docker-entrypoint +14 -0
  43. data/templates/compose.yml +7 -0
  44. data/templates/config/initializers/environment.rb +5 -8
  45. data/templates/config/initializers/filter_parameter_logging.rb +3 -0
  46. data/templates/config/initializers/opentelemetry.rb +32 -0
  47. data/templates/config/locales/en.yml +32 -0
  48. data/templates/config/locales/settings/en.yml +5 -0
  49. data/templates/lib/plug_app/schemas/api/2023-03-06/components/schemas/yetto.json +2 -2
  50. data/templates/lib/plug_app/schemas/api/2023-03-06/openapi.json +4 -4
  51. data/templates/lib/plug_app/schemas/api/2023-03-06/paths/plug.json +1 -1
  52. data/templates/lib/plug_app/schemas/api/2023-03-06/paths/yetto/after_create_message.json +2 -2
  53. data/templates/lib/plug_app/schemas/api/2023-03-06/paths/yetto/after_create_plug_installation.json +2 -2
  54. data/templates/lib/tasks/test_tasks.rake +6 -2
  55. data/templates/script/edit-credentials +29 -0
  56. data/templates/script/hmac_text +1 -1
  57. data/templates/script/licenses +4 -48
  58. data/templates/script/server +62 -2
  59. data/templates/script/sorbet +7 -0
  60. data/templates/test/controllers/application_controller_test.rb +32 -0
  61. data/templates/test/controllers/settings_controller_test.rb +1 -1
  62. data/templates/test/controllers/yetto_controller_test.rb +1 -1
  63. data/templates/test/fixtures/files/fake_pem_file/fake.pem +27 -0
  64. data/templates/test/jobs/update_yetto_job_test.rb +3 -18
  65. data/templates/test/support/api.rb +1 -1
  66. data/templates/test/support/rails.rb +1 -1
  67. data/templates/test/support/webmocks/slack_webmock.rb +2 -2
  68. data/templates/test/support/webmocks/yetto_webmock.rb +119 -0
  69. data/templates/test/test_helper.rb +16 -3
  70. data/templates/vendor/fly/fly-production.toml +38 -0
  71. data/templates/vendor/fly/fly-staging.toml +33 -0
  72. metadata +39 -16
  73. data/templates/.env.test +0 -4
  74. data/templates/.github/actions/license/action.yml +0 -11
  75. data/templates/.github/actions/setup/action.yml +0 -10
  76. data/templates/.github/actions/sisyphus/action.yml +0 -11
  77. data/templates/.github/actions/sorbet/action.yml +0 -19
  78. data/templates/app/views/settings/index.json.jbuilder +0 -15
  79. data/templates/config/initializers/open_telemetry.rb +0 -27
  80. data/templates/script/security_checks/brakeman +0 -5
  81. data/templates/script/security_checks/bundle-audit +0 -5
  82. data/templates/script/server-debug +0 -5
  83. data/templates/script/typecheck +0 -44
  84. data/templates/test/fixtures/files/.keep +0 -0
  85. data/templates/test/support/webmocks/yetto.rb +0 -94
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA256:
3
- metadata.gz: ec50cd2cc85932b748a97df9741291de3651b88ab8d06584f96d2a03ad474a73
4
- data.tar.gz: ade4d54823ec4a179234a259dd4ac1ae05f6e9228aa52955529043a473d35821
3
+ metadata.gz: f53e25251ab0f4ba3f9150cee67fbf2f2002e892431c7c66d288d17887e86274
4
+ data.tar.gz: a8262fe4f7001373e62a48de343016a6787360d8a73c34510476ea45bc1d6703
5
5
  SHA512:
6
- metadata.gz: 9c4c51dd65cb697d9eee304fd7a6915af8301cbf4fbab804fe17c06f0b50142f72d61914d2d10403f04de6f67b916f7f9b4b93b99d83833769fdf63860fa2fef
7
- data.tar.gz: 4190712ab8505f2e450911a32bd860a0e811129934f817d1f3a6bb80297e0b9bc3b3fd2555a10df39a72c95548bfe044b974a75bf321b8ee51920b2f77401786
6
+ metadata.gz: 6a7389980993930ae1d91f62247767607f963a10ae25bf0ad8cf4c686db6dccf34972a7fd87f851e047a0917432a88d832c9ded9fe5873ef182f08785ca55cb3
7
+ data.tar.gz: 5fa77ba49059630eebb5a6f9ae45e478d8cde9bb3920bdd04bf238363b2aa20af19297ce5c8aedfaa5c1d29bbd972c9c79f73c5f0d9a975d7e3bd64c257b09d1
data/CHANGELOG.md CHANGED
@@ -1,3 +1,7 @@
1
+ ## [v0.2.1] - 11-07-2023
2
+ null
3
+ ## [v0.2.0] - 11-07-2023
4
+ null
1
5
  # Changelog
2
6
 
3
7
  ## [v0.1.3](https://github.com/yettoapp/hephaestus/tree/v0.1.3) (2023-03-15)
data/README.md CHANGED
@@ -10,12 +10,38 @@ gem install hephaestus
10
10
  hephaestus plug-app
11
11
  ```
12
12
 
13
- If you're working on updating this locally, you may also probably want:
13
+ Where `app` represents the name of the platform you'd like to interact with `jira`, `notion`, `slack`, etc.
14
+
15
+ If you're working on updating/testing this gem locally, you may also want:
14
16
 
15
17
  ```
16
18
  rm -rf plug-app && DEBUG=1 hephaestus/bin/hephaestus plug-app
17
19
  ```
18
20
 
21
+ This way you can wipe the dir and quickly iterate on new changes.
22
+
23
+ ## Building upon it
24
+
25
+ ### Launching the server
26
+
27
+ First, you'll note that you have a `script/ngrok` file, which launches an ngrok server at `https://plug-app.ngrok.io`, which maps locally to `http://localhost:6661`. This can be essential when testing the platform locally for the first time. (Keep in mind that you still need to run `script/server` to actually start the local server—this is just to help facilitate communication with the platform.)
28
+
29
+ ### Setting up routes
30
+
31
+ You should probably open up config/routes.rb to make modifications to any incoming (from the platform) or outgoing (for Yetto) HTTP flows.
32
+
33
+ ### Defining settings
34
+
35
+ Next, you'll want to open `app/views/settings/new.json.jbuilder` and modify the JSON structure of the Settings form page users will see when they first install the plug. Note that this adheres to a strict schema.
36
+
37
+ ### Accepting events
38
+
39
+ After a user submits a plug installation on the Yetto side, it'll send a POST payload to `/api/:version/:event/:record_type`--for example, `/api/2023-03-06/after/plug_installation`. Open up the `yetto_controller.rb` file and decide what happens next!
40
+
41
+ ### Creating services
42
+
43
+ Any code which communicates with the third party should be placed in the `app/services` directory. A generic HTTP service is included.
44
+
19
45
  ## Acknowledgements
20
46
 
21
47
  This project was heavily based on [thoughtbot/suspenders](https://github.com/thoughtbot/suspenders).
data/bin/hephaestus CHANGED
@@ -2,6 +2,7 @@
2
2
  # frozen_string_literal: true
3
3
 
4
4
  require "pathname"
5
+ require 'rainbow'
5
6
 
6
7
  source_path = (Pathname.new(__FILE__).dirname + "../lib").expand_path
7
8
  $LOAD_PATH << source_path
@@ -47,12 +48,17 @@ end
47
48
 
48
49
  path = ARGV.first
49
50
  if File.exist?(path)
50
- puts "The directory #{path} already exists."
51
+ puts Rainbow("\nError: The directory #{path} already exists.").red
51
52
  exit 1
52
53
  end
53
54
 
54
55
  unless path.start_with?("plug-")
55
- puts "The directory name must start with 'plug-'"
56
+ puts Rainbow("\nError: The directory name must start with 'plug-'").red
57
+ exit 1
58
+ end
59
+
60
+ unless path.length > "plug-".length
61
+ puts Rainbow("\nError: The directory name must start with 'plug-'").red
56
62
  exit 1
57
63
  end
58
64
 
@@ -64,5 +70,5 @@ ARGV.push("--minimal")
64
70
  ARGV.push("--no-skip-active-job")
65
71
  ARGV.push("--skip-asset-pipeline")
66
72
  ARGV.push("--skip-active-record")
67
- ARGV.push("--skip-active-record")
73
+
68
74
  Hephaestus::AppGenerator.start
@@ -17,6 +17,7 @@ module Hephaestus
17
17
  copy_file("hephaestus_gitignore", ".gitignore")
18
18
  end
19
19
 
20
+ # it is, apparently, extraordinarly important to keep this as an erb
20
21
  def gemfile
21
22
  template("Gemfile.erb", "Gemfile")
22
23
  end
@@ -30,8 +31,7 @@ module Hephaestus
30
31
  end
31
32
 
32
33
  def copy_setup_scripts
33
- source = File.join(Hephaestus::AppGenerator.source_root, "script")
34
- directory(source, "script")
34
+ directory(Hephaestus.source_path("script"), "script")
35
35
  Dir.glob("script/**/*").each do |file|
36
36
  next if File.directory?(file)
37
37
 
@@ -81,6 +81,19 @@ module Hephaestus
81
81
  configure_environment("test", config)
82
82
  end
83
83
 
84
+ def setup_ssl
85
+ ssl = <<~SSL
86
+ config.force_ssl = true
87
+ config.ssl_options = { hsts: { subdomains: true, preload: true, expires: 1.year } }
88
+ SSL
89
+
90
+ replace_in_file(
91
+ "config/environments/production.rb",
92
+ "# config.force_ssl = true",
93
+ ssl,
94
+ )
95
+ end
96
+
84
97
  def setup_staging_environment
85
98
  FileUtils.cp(File.join(destination_root, "config/environments/production.rb"), File.join(destination_root, "config/environments/staging.rb"))
86
99
  end
@@ -95,6 +108,10 @@ module Hephaestus
95
108
  end
96
109
  end
97
110
 
111
+ def restore_gemfile
112
+ replace_in_file("Gemfile", /gem "hephaestus".+/, "gem \"hephaestus\"")
113
+ end
114
+
98
115
  def ruby_version
99
116
  create_file(".ruby-version", "#{Hephaestus::RUBY_VERSION}\n")
100
117
  end
@@ -104,7 +121,7 @@ module Hephaestus
104
121
  end
105
122
 
106
123
  def create_github_repo(repo_name)
107
- run("gh repo create #{repo_name}")
124
+ run("gh repo create #{repo_name}", exit_on_failure: false)
108
125
  end
109
126
 
110
127
  def remove_config_comment_lines
@@ -139,12 +156,16 @@ module Hephaestus
139
156
  end
140
157
 
141
158
  def replace_generic_variables
142
- replace_in_files(destination_root, "${APP}", short_app_name.capitalize)
143
- replace_in_files(destination_root, "${app}", short_app_name.downcase)
159
+ say(set_color("Replacing generic variable names...", :cyan))
160
+ replace_in_files(destination_root, /App(?!lication)/, short_app_name.capitalize)
161
+ replace_in_files(destination_root, %r{(?<!yetto)app(?!lication|/|roximate)}, short_app_name.downcase)
144
162
  replace_in_files(destination_root, "PlugApp", app_name.underscore.camelcase)
145
163
  replace_in_files(destination_root, "plug-app", app_name.dasherize)
146
164
  replace_in_files(destination_root, "PLUG_APP", app_name.underscore.upcase)
147
165
  replace_in_files(destination_root, "plug_app", app_name.underscore)
166
+
167
+ # this is erroneously changed
168
+ replace_in_file("script/server", "/usr/src/#{short_app_name.downcase}", "/usr/src/app")
148
169
  end
149
170
 
150
171
  private
@@ -8,10 +8,10 @@ module Hephaestus
8
8
  module ExitOnFailure
9
9
  extend ActiveSupport::Concern
10
10
 
11
- # def bundle_command(*args)
12
- # run("bundle", args)
13
- # exit(false) if $CHILD_STATUS.exitstatus.nonzero?
14
- # end
11
+ def bundle_command(*)
12
+ super
13
+ exit(false) if $CHILD_STATUS.exitstatus.nonzero?
14
+ end
15
15
 
16
16
  module ClassMethods
17
17
  def exit_on_failure?
@@ -3,6 +3,7 @@
3
3
 
4
4
  require "rails/generators"
5
5
  require "rails/generators/rails/app/app_generator"
6
+ require "tempfile"
6
7
 
7
8
  module Hephaestus
8
9
  class AppGenerator < Rails::Generators::AppGenerator
@@ -23,62 +24,123 @@ module Hephaestus
23
24
  desc: "Show this help message and quit"
24
25
 
25
26
  def finish_template
26
- say("Invoking Hephaestus customization")
27
27
  invoke(:hephaestus_customization)
28
28
  super
29
29
  end
30
30
 
31
+ # NOTE: this function name is important as it overrides
32
+ # a Rails function of the same name (that function performs work
33
+ # that we don't want to do)
31
34
  def leftovers
32
35
  build(:replace_generic_variables)
33
- generate("hephaestus:license")
34
- generate("hephaestus:rubocop")
35
36
 
36
- generate("hephaestus:sorbet")
37
- invoke(:commit)
37
+ say(set_color("Generating `hephaestus:license`...", :cyan))
38
+ capture_stdout do
39
+ generate("hephaestus:license")
40
+ end
41
+ say(set_color("Generating `hephaestus:rubocop`...", :cyan))
42
+ capture_stdout do
43
+ generate("hephaestus:rubocop")
44
+ end
45
+ say(set_color("Generating `hephaestus:sorbet`...", :cyan))
46
+ capture_stdout do
47
+ generate("hephaestus:sorbet")
48
+ end
49
+ say(set_color("Creating first commit...", :cyan))
50
+ capture_stdout do
51
+ invoke(:commit)
52
+ end
53
+
54
+ build(:restore_gemfile)
38
55
  invoke(:outro)
39
56
  end
40
57
 
41
58
  def hephaestus_customization
59
+ say(set_color("Invoking Hephaestus customizations...", :cyan))
60
+
61
+ run("rails app:update:bin", capture: true)
42
62
  invoke(:customize_gemfile)
63
+
43
64
  invoke(:copy_github_actions)
65
+ invoke(:copy_vscode_settings)
66
+
44
67
  invoke(:setup_development_environment)
45
- invoke(:setup_staging_environment)
46
68
  invoke(:setup_production_environment)
69
+ invoke(:setup_staging_environment)
47
70
  invoke(:setup_test_environment)
71
+ invoke(:setup_shared_environment_logic)
72
+
48
73
  invoke(:configure_app)
49
- invoke(:purge_unneeded_files)
50
- invoke(:copy_vscode_settings)
51
- invoke(:generate_default)
52
74
  invoke(:create_github_repo)
53
75
  end
54
76
 
55
77
  def customize_gemfile
78
+ say(set_color("Customizing Gemfile...", :cyan))
56
79
  build(:replace_gemfile)
57
- bundle_command("install")
58
- bundle_command("lock --add-platform x86_64-linux")
80
+ capture_stdout do
81
+ bundle_command("install")
82
+ bundle_command("lock --add-platform x86_64-linux")
83
+ end
59
84
  end
60
85
 
61
86
  def copy_github_actions
62
- source = File.join(Hephaestus::AppGenerator.source_root, ".github")
63
- directory(source, ".github")
87
+ say(set_color("Copying GitHub Actions...", :cyan))
88
+
89
+ capture_stdout do
90
+ directory(Hephaestus.source_path(".github"), ".github")
91
+ end
92
+ end
93
+
94
+ def copy_vscode_settings
95
+ say(set_color("Copying .vscode/...", :cyan))
96
+
97
+ capture_stdout do
98
+ directory(Hephaestus.source_path(".vscode"), ".vscode")
99
+ end
64
100
  end
65
101
 
66
102
  def setup_development_environment
67
- say("Setting up the development environment")
68
- build(:configure_local_mail)
69
- build(:raise_on_delivery_errors)
70
- build(:configure_dev_hosting)
71
- build(:copy_setup_scripts)
103
+ say(set_color("Setting up the development environment...", :cyan))
104
+ capture_stdout do
105
+ build(:raise_on_delivery_errors)
106
+ build(:configure_dev_hosting)
107
+ build(:copy_setup_scripts)
108
+ end
72
109
  end
73
110
 
74
- def copy_vscode_settings
75
- source = File.join(Hephaestus::AppGenerator.source_root, ".vscode")
76
- directory(source, ".vscode")
111
+ def setup_production_environment
112
+ say(set_color("Setting up the production environment...", :cyan))
113
+ capture_stdout do
114
+ build(:setup_asset_host)
115
+ build(:setup_ssl)
116
+ end
77
117
  end
78
118
 
79
- def purge_unneeded_files
119
+ def setup_staging_environment
120
+ say(set_color("Setting up the staging environment...", :cyan))
121
+ capture_stdout do
122
+ build(:setup_staging_environment)
123
+ end
124
+ end
125
+
126
+ def setup_test_environment
127
+ say(set_color("Setting up the test environment...", :cyan))
128
+ capture_stdout do
129
+ build(:setup_test_environment)
130
+ end
131
+ end
132
+
133
+ def setup_shared_environment_logic
134
+ capture_stdout do
135
+ build(:setup_background_worker)
136
+ build(:setup_slack_logger)
137
+ end
138
+ end
139
+
140
+ def configure_app
141
+ say(set_color("Configuring app...", :cyan))
142
+
80
143
  remove_dir("app/assets")
81
- remove_file("app/controllers/concerns/.keep")
82
144
  remove_dir("app/helpers")
83
145
  remove_dir("app/models")
84
146
  remove_dir("app/views/layouts")
@@ -87,56 +149,67 @@ module Hephaestus
87
149
  remove_dir("test/helpers")
88
150
  remove_dir("test/channels")
89
151
  remove_dir("test/models")
90
- end
91
152
 
92
- def setup_staging_environment
93
- build(:setup_staging_environment)
94
- end
153
+ build(:configure_time_formats)
95
154
 
96
- def setup_production_environment
97
- say("Setting up the production environment")
98
- build(:setup_asset_host)
99
- build(:setup_background_worker)
100
- build(:setup_slack_logger)
101
- end
155
+ bundle_command("binstubs bundler")
102
156
 
103
- def setup_test_environment
104
- say("Setting up the test environment")
105
- build(:setup_test_environment)
106
- end
157
+ capture_stdout do
158
+ generate("hephaestus:core")
159
+ generate("hephaestus:deployment")
160
+ generate("hephaestus:lib")
107
161
 
108
- def configure_app
109
- say("Configuring app")
110
- build(:configure_time_formats)
162
+ # keep this at the end
163
+ generate("hephaestus:config")
164
+ end
111
165
  end
112
166
 
113
167
  def create_github_repo
114
168
  if !options[:skip_git] && options[:github]
115
- say("Creating Github repo")
169
+ say(set_color("Creating repository via `gh repo`...", :cyan))
116
170
  build(:create_github_repo, options[:github])
117
171
  end
118
172
  end
119
173
 
120
- def generate_default
121
- run("spring stop > /dev/null 2>&1 || true")
122
-
123
- generate("hephaestus:core")
124
- generate("hephaestus:deployment")
125
- generate("hephaestus:lib")
126
-
127
- # keep this at the end
128
- generate("hephaestus:config")
129
- end
130
-
131
174
  def commit
132
175
  run("git add .")
133
- run("git commit -m 'Initial commit'")
176
+ run("git commit -m 'Initial commit'", capture: true)
134
177
  end
135
178
 
136
179
  def outro
137
- say("\nCongratulations! You just made a plug.")
138
- say("\nTry running `rails c` to ensure that everything was set up correctly.")
139
- say("\nRunning `rake test` is also a good idea.")
180
+ say(<<~OUTPUT)
181
+
182
+ #{set_color("Congratulations!", :green)} You just made a Yetto plug.
183
+
184
+ You'll need to `cd #{ARGV.first}` and run the following commands--I can't do it for you!
185
+
186
+ * `bin/rails credentials:edit --environment development`
187
+
188
+ #{set_color("WAIT!", :red)} After running this command, note that Rails credited a file called development.key in the config/credentials directory.
189
+ Store this in 1Password, then change the .env file to use this value. Generate keys for staging/production, too:
190
+
191
+ * `bin/rails credentials:edit --environment staging`
192
+ `bin/rails credentials:edit --environment production`
193
+
194
+ Store this in 1Password too; you don't need the .env file for staging/production.
195
+
196
+ For `SIGNING_SECRET` and `YETTO_PLUG_ID`, you'll need to generate those values yourself.
197
+
198
+ Then, try running `bin/rails c` to ensure that everything was set up correctly.
199
+ Running `rake test` is also a good idea.
200
+
201
+ #{set_color("Also, after pushing to GitHub:", :yellow)}
202
+
203
+ * Set `settings/branches` to protect `production`
204
+ * ✅ Require status checks to pass before merging
205
+ * 🖊️ Status checks that are required: `test`, `ruby / brakeman`, `ruby / bundle-audit`.
206
+ You can only set those 👆 after you've opened the first PR on GitHub. Crazy, I know!!
207
+ But, doing so is *essential* for automerge to function properly.
208
+
209
+ * Speaking of which, in `/settings`
210
+ * ✅ Allow auto-merge
211
+ * ✅ Automatically delete head branches
212
+ OUTPUT
140
213
  end
141
214
 
142
215
  class << self
@@ -154,5 +227,24 @@ module Hephaestus
154
227
  def using_active_record?
155
228
  !options[:skip_active_record]
156
229
  end
230
+
231
+ private def capture_stdout
232
+ stream = "stdout"
233
+ captured_stream = Tempfile.new(stream)
234
+ stream_io = eval("$#{stream}", binding, __FILE__, __LINE__)
235
+ origin_stream = stream_io.dup
236
+ stream_io.reopen(captured_stream)
237
+
238
+ yield
239
+
240
+ stream_io.rewind
241
+ captured_stream.read
242
+ ensure
243
+ unless captured_stream.nil?
244
+ captured_stream.close
245
+ captured_stream.unlink
246
+ end
247
+ stream_io.reopen(origin_stream) unless stream_io.nil?
248
+ end
157
249
  end
158
250
  end
@@ -26,9 +26,20 @@ module Hephaestus
26
26
  before: "class Application < Rails::Application",
27
27
  )
28
28
 
29
+ raltie_overload = <<~CONFIG
30
+
31
+ # Load dotenv only in development environment
32
+ Dotenv::Railtie.overload if Rails.env.development?
33
+ CONFIG
34
+ inject_into_file(
35
+ "config/application.rb",
36
+ raltie_overload,
37
+ after: "Bundler.require(*Rails.groups)",
38
+ )
39
+
29
40
  config = <<~CONFIG
30
41
 
31
- # Only loads a smaller set of middleware suitable for API only apps.
42
+ # Only loads a smaller set of middleware suitable for API-only Rails.
32
43
  # Middleware like session, flash, cookies can be added back manually.
33
44
  # Skip views, helpers and assets when generating a new resource.
34
45
  config.api_only = true
@@ -77,15 +88,28 @@ module Hephaestus
77
88
  root "root#index"
78
89
 
79
90
  # events into the plug, usually from yetto
80
- get "/api/2023-03-06/settings", to: "settings#index"
91
+ get "/api/2023-03-06/settings", to: "settings#new"
81
92
  post "/api/2023-03-06/:event/:record_type", to: "yetto#event"
82
93
 
94
+ # inbound message
95
+ post "/app/2023-03-06/webhook/:organization_id/:inbox_id/:plug_installation_id", to: "app#webhook"
96
+ # post "/app/2023-03-06/webhook/inbound", to: "app#process_inbound" # for generic inbound pings
97
+
83
98
  # Staff pages
84
99
  get "staff", to: "staff#index"
85
100
  require "sidekiq/web"
86
101
  constraints ->(request) { StaffController.staff_request?(request) } do
87
102
  mount Sidekiq::Web => "staff/sidekiq"
88
103
  end
104
+
105
+ #############################################
106
+ # error pages -- these MUST be at the end! ##
107
+ #############################################
108
+
109
+ get "/500", to: "application#render500" if Rails.env.production? || Rails.env.staging?
110
+
111
+ match "/", to: "application#not_found", via: :all
112
+ match "/*unmatched_route", to: "application#not_found", via: :all
89
113
  ROUTES
90
114
 
91
115
  replace_in_file(
@@ -98,5 +122,9 @@ module Hephaestus
98
122
  def sidekiq
99
123
  copy_file("config/sidekiq.yml", "config/sidekiq.yml")
100
124
  end
125
+
126
+ def credentials
127
+ remove_file("config/credentials.yml.enc")
128
+ end
101
129
  end
102
130
  end
@@ -13,6 +13,7 @@ module Hephaestus
13
13
  copy_file("app/controllers/settings_controller.rb", "app/controllers/settings_controller.rb")
14
14
  copy_file("app/controllers/staff_controller.rb", "app/controllers/staff_controller.rb")
15
15
  copy_file("app/controllers/yetto_controller.rb", "app/controllers/yetto_controller.rb")
16
+ copy_file("app/controllers/app_controller.rb", "app/controllers/#{short_app_name}_controller.rb")
16
17
 
17
18
  copy_file("app/controllers/concerns/authable.rb", "app/controllers/concerns/authable.rb")
18
19
  end
@@ -26,6 +27,34 @@ module Hephaestus
26
27
  copy_file("app/lib/body_parameter/yetto_parameters.rb", "app/lib/body_parameter/yetto_parameters.rb")
27
28
  copy_file("app/lib/constants/app.rb", "app/lib/constants/plug_#{short_app_name}.rb")
28
29
  copy_file("app/lib/headers/yetto.rb", "app/lib/headers/yetto.rb")
30
+
31
+ path_parameters_content = <<~CONTENT
32
+ # typed: false
33
+ # frozen_string_literal: true
34
+
35
+ module PathParameter
36
+ module AppParameters
37
+ extend T::Sig
38
+ end
39
+ end
40
+ CONTENT
41
+
42
+ create_file("app/lib/path_parameter/#{short_app_name}_parameters.rb", path_parameters_content)
43
+
44
+ body_parameters_content = <<~CONTENT
45
+ # typed: false
46
+ # frozen_string_literal: true
47
+
48
+ module BodyParameter
49
+ module AppParameters
50
+ extend T::Sig
51
+ end
52
+ end
53
+ CONTENT
54
+
55
+ create_file("app/lib/body_parameter/#{short_app_name}_parameters.rb", body_parameters_content)
56
+
57
+ copy_file("app/lib/path_parameter/settings_parameters.rb", "app/lib/path_parameter/settings_parameters.rb")
29
58
  copy_file("app/lib/path_parameter/yetto_parameters.rb", "app/lib/path_parameter/yetto_parameters.rb")
30
59
  directory("app/lib/plug_app", "app/lib/#{app_name.underscore}")
31
60
 
@@ -43,7 +72,7 @@ module Hephaestus
43
72
  end
44
73
 
45
74
  def views
46
- copy_file("app/views/settings/index.json.jbuilder", "app/views/settings/index.json.jbuilder")
75
+ copy_file("app/views/settings/new.json.jbuilder", "app/views/settings/new.json.jbuilder")
47
76
  end
48
77
  end
49
78
  end
@@ -10,9 +10,15 @@ module Hephaestus
10
10
  copy_file("Procfile.debug", "Procfile.debug")
11
11
  end
12
12
 
13
- def sample_env
14
- copy_file(".env.test", ".env.test")
15
- copy_file(".env.test", ".env")
13
+ def dotenv
14
+ copy_file(".env.sample", ".env")
15
+ copy_file(".env.sample", ".env.sample")
16
+ end
17
+
18
+ def docker
19
+ copy_file("compose.yml", "compose.yml")
20
+ copy_file("Dockerfile", "Dockerfile")
21
+ copy_file("bin/docker-entrypoint", "bin/docker-entrypoint")
16
22
  end
17
23
  end
18
24
  end
@@ -7,6 +7,7 @@ module Hephaestus
7
7
  class LibGenerator < Generators::Base
8
8
  def lib_plug
9
9
  directory("lib/plug_app", "lib/#{app_name.underscore}")
10
+ remove_file("lib/constants/plug-#{short_app_name}.rb")
10
11
  end
11
12
 
12
13
  def lib_tasks
@@ -10,7 +10,7 @@ module Hephaestus
10
10
  Bundler.with_unbundled_env do
11
11
  run("bundle exec tapioca init")
12
12
  run("bundle exec tapioca require")
13
- run("script/typecheck --update")
13
+ run("script/sorbet --update")
14
14
  end
15
15
  end
16
16
  end
@@ -2,7 +2,7 @@
2
2
  # frozen_string_literal: true
3
3
 
4
4
  module Hephaestus
5
- VERSION = "0.1.3"
5
+ VERSION = "0.2.2"
6
6
  RAILS_VERSION = "~> 7.0.0"
7
7
  RUBY_VERSION = File
8
8
  .read("#{File.dirname(__FILE__)}/../../.ruby-version")
data/lib/hephaestus.rb CHANGED
@@ -19,3 +19,11 @@ end
19
19
  require "hephaestus/actions"
20
20
  require "hephaestus/actions/strip_comments_action"
21
21
  require "hephaestus/app_builder"
22
+
23
+ module Hephaestus
24
+ class << self
25
+ def source_path(root)
26
+ File.join(Hephaestus::AppGenerator.source_root, root)
27
+ end
28
+ end
29
+ end