rolemodel-rails 0.26.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 +7 -0
- data/LICENSE.txt +21 -0
- data/README.md +161 -0
- data/Rakefile +6 -0
- data/lib/generators/rolemodel/README.md +29 -0
- data/lib/generators/rolemodel/USAGE +5 -0
- data/lib/generators/rolemodel/all_generator.rb +29 -0
- data/lib/generators/rolemodel/base_generator.rb +14 -0
- data/lib/generators/rolemodel/editors/README.md +9 -0
- data/lib/generators/rolemodel/editors/USAGE +9 -0
- data/lib/generators/rolemodel/editors/editors_generator.rb +30 -0
- data/lib/generators/rolemodel/editors/vscode_helpers.rb +22 -0
- data/lib/generators/rolemodel/github/README.md +23 -0
- data/lib/generators/rolemodel/github/USAGE +9 -0
- data/lib/generators/rolemodel/github/github_generator.rb +43 -0
- data/lib/generators/rolemodel/good_job/README.md +13 -0
- data/lib/generators/rolemodel/good_job/USAGE +5 -0
- data/lib/generators/rolemodel/good_job/good_job_generator.rb +73 -0
- data/lib/generators/rolemodel/good_job/templates/config/initializers/active_job.rb +17 -0
- data/lib/generators/rolemodel/good_job/templates/config/initializers/good_job.rb +24 -0
- data/lib/generators/rolemodel/heroku/README.md +8 -0
- data/lib/generators/rolemodel/heroku/USAGE +9 -0
- data/lib/generators/rolemodel/heroku/heroku_generator.rb +52 -0
- data/lib/generators/rolemodel/heroku/templates/Procfile +2 -0
- data/lib/generators/rolemodel/heroku/templates/app.json.tt +30 -0
- data/lib/generators/rolemodel/kaminari/README.md +14 -0
- data/lib/generators/rolemodel/kaminari/USAGE +5 -0
- data/lib/generators/rolemodel/kaminari/kaminari_generator.rb +17 -0
- data/lib/generators/rolemodel/kaminari/templates/app/views/kaminari/_first_page.html.slim +9 -0
- data/lib/generators/rolemodel/kaminari/templates/app/views/kaminari/_gap.html.slim +8 -0
- data/lib/generators/rolemodel/kaminari/templates/app/views/kaminari/_last_page.html.slim +9 -0
- data/lib/generators/rolemodel/kaminari/templates/app/views/kaminari/_next_page.html.slim +12 -0
- data/lib/generators/rolemodel/kaminari/templates/app/views/kaminari/_page.html.slim +10 -0
- data/lib/generators/rolemodel/kaminari/templates/app/views/kaminari/_paginator.html.slim +19 -0
- data/lib/generators/rolemodel/kaminari/templates/app/views/kaminari/_prev_page.html.slim +12 -0
- data/lib/generators/rolemodel/linters/README.md +32 -0
- data/lib/generators/rolemodel/linters/USAGE +5 -0
- data/lib/generators/rolemodel/linters/all_generator.rb +14 -0
- data/lib/generators/rolemodel/linters/eslint/README.md +5 -0
- data/lib/generators/rolemodel/linters/eslint/USAGE +8 -0
- data/lib/generators/rolemodel/linters/eslint/eslint_generator.rb +33 -0
- data/lib/generators/rolemodel/linters/eslint/templates/eslint.config.js +92 -0
- data/lib/generators/rolemodel/linters/rubocop/README.md +7 -0
- data/lib/generators/rolemodel/linters/rubocop/USAGE +9 -0
- data/lib/generators/rolemodel/linters/rubocop/rubocop_generator.rb +23 -0
- data/lib/generators/rolemodel/linters/rubocop/templates/lib/cops/form_error_response.rb +54 -0
- data/lib/generators/rolemodel/linters/rubocop/templates/lib/cops/no_chrome_tag.rb +45 -0
- data/lib/generators/rolemodel/lograge/README.md +10 -0
- data/lib/generators/rolemodel/lograge/USAGE +8 -0
- data/lib/generators/rolemodel/lograge/lograge_generator.rb +15 -0
- data/lib/generators/rolemodel/lograge/templates/config/initializers/lograge.rb +16 -0
- data/lib/generators/rolemodel/mailers/README.md +13 -0
- data/lib/generators/rolemodel/mailers/USAGE +22 -0
- data/lib/generators/rolemodel/mailers/mailers_generator.rb +99 -0
- data/lib/generators/rolemodel/mailers/templates/app/assets/stylesheets/mailer.scss +61 -0
- data/lib/generators/rolemodel/mailers/templates/app/mailers/example_mailer.rb +8 -0
- data/lib/generators/rolemodel/mailers/templates/app/mailers/staging_mailer_interceptor.rb +9 -0
- data/lib/generators/rolemodel/mailers/templates/app/views/example_mailer/example_email.html.slim +16 -0
- data/lib/generators/rolemodel/mailers/templates/app/views/layouts/mailer.html.slim +16 -0
- data/lib/generators/rolemodel/mailers/templates/config/initializers/premailer_rails.rb +15 -0
- data/lib/generators/rolemodel/mailers/templates/public/logo.png +0 -0
- data/lib/generators/rolemodel/mailers/templates/spec/mailers/previews/example_mailer_preview.rb +6 -0
- data/lib/generators/rolemodel/optics/README.md +8 -0
- data/lib/generators/rolemodel/optics/USAGE +5 -0
- data/lib/generators/rolemodel/optics/all_generator.rb +12 -0
- data/lib/generators/rolemodel/optics/base/README.md +9 -0
- data/lib/generators/rolemodel/optics/base/USAGE +5 -0
- data/lib/generators/rolemodel/optics/base/base_generator.rb +21 -0
- data/lib/generators/rolemodel/optics/icons/README.md +7 -0
- data/lib/generators/rolemodel/optics/icons/USAGE +8 -0
- data/lib/generators/rolemodel/optics/icons/icons_generator.rb +48 -0
- data/lib/generators/rolemodel/optics/icons/templates/app/helpers/icon_helper.rb.tt +24 -0
- data/lib/generators/rolemodel/optics/icons/templates/app/icon_builders/custom_icon_builder.rb +53 -0
- data/lib/generators/rolemodel/optics/icons/templates/app/icon_builders/feather_icon_builder.rb +22 -0
- data/lib/generators/rolemodel/optics/icons/templates/app/icon_builders/icon_builder.rb +73 -0
- data/lib/generators/rolemodel/optics/icons/templates/app/icon_builders/lucide_icon_builder.rb +22 -0
- data/lib/generators/rolemodel/optics/icons/templates/app/icon_builders/material_icon_builder.rb +31 -0
- data/lib/generators/rolemodel/optics/icons/templates/app/icon_builders/phosphor_icon_builder.rb +27 -0
- data/lib/generators/rolemodel/optics/icons/templates/app/icon_builders/tabler_icon_builder.rb +22 -0
- data/lib/generators/rolemodel/react/README.md +12 -0
- data/lib/generators/rolemodel/react/USAGE +5 -0
- data/lib/generators/rolemodel/react/react_generator.rb +36 -0
- data/lib/generators/rolemodel/react/templates/app/helpers/react_helper.rb +11 -0
- data/lib/generators/rolemodel/react/templates/app/javascript/components/HelloReact.jsx +14 -0
- data/lib/generators/rolemodel/react/templates/app/javascript/controllers/react_controller.js +24 -0
- data/lib/generators/rolemodel/readme/README.md +9 -0
- data/lib/generators/rolemodel/readme/USAGE +8 -0
- data/lib/generators/rolemodel/readme/readme_generator.rb +11 -0
- data/lib/generators/rolemodel/readme/templates/README.md.erb +116 -0
- data/lib/generators/rolemodel/replace_content_helper.rb +29 -0
- data/lib/generators/rolemodel/saas/README.md +7 -0
- data/lib/generators/rolemodel/saas/USAGE +5 -0
- data/lib/generators/rolemodel/saas/all_generator.rb +15 -0
- data/lib/generators/rolemodel/saas/devise/README.md +24 -0
- data/lib/generators/rolemodel/saas/devise/USAGE +25 -0
- data/lib/generators/rolemodel/saas/devise/devise_generator.rb +172 -0
- data/lib/generators/rolemodel/saas/devise/templates/app/assets/stylesheets/login.css +30 -0
- data/lib/generators/rolemodel/saas/devise/templates/app/controllers/admin/users_controller.rb +34 -0
- data/lib/generators/rolemodel/saas/devise/templates/app/controllers/application_controller.rb +11 -0
- data/lib/generators/rolemodel/saas/devise/templates/app/controllers/users/invitations_controller.rb +77 -0
- data/lib/generators/rolemodel/saas/devise/templates/app/controllers/users/omniauth_callbacks_controller.rb +30 -0
- data/lib/generators/rolemodel/saas/devise/templates/app/controllers/users/registrations_controller.rb +80 -0
- data/lib/generators/rolemodel/saas/devise/templates/app/views/admin/users/edit.html.slim +10 -0
- data/lib/generators/rolemodel/saas/devise/templates/app/views/admin/users/index.html.slim +27 -0
- data/lib/generators/rolemodel/saas/devise/templates/app/views/devise/confirmations/new.html.slim +11 -0
- data/lib/generators/rolemodel/saas/devise/templates/app/views/devise/invitations/edit.html.slim +13 -0
- data/lib/generators/rolemodel/saas/devise/templates/app/views/devise/invitations/new.html.slim +14 -0
- data/lib/generators/rolemodel/saas/devise/templates/app/views/devise/mailer/confirmation_instructions.html.slim +3 -0
- data/lib/generators/rolemodel/saas/devise/templates/app/views/devise/mailer/email_changed.html.slim +5 -0
- data/lib/generators/rolemodel/saas/devise/templates/app/views/devise/mailer/invitation_instructions.html.slim +11 -0
- data/lib/generators/rolemodel/saas/devise/templates/app/views/devise/mailer/invitation_instructions.text.slim +6 -0
- data/lib/generators/rolemodel/saas/devise/templates/app/views/devise/mailer/password_change.html.slim +2 -0
- data/lib/generators/rolemodel/saas/devise/templates/app/views/devise/mailer/reset_password_instructions.html.slim +5 -0
- data/lib/generators/rolemodel/saas/devise/templates/app/views/devise/mailer/unlock_instructions.html.slim +4 -0
- data/lib/generators/rolemodel/saas/devise/templates/app/views/devise/passwords/edit.html.slim +13 -0
- data/lib/generators/rolemodel/saas/devise/templates/app/views/devise/passwords/new.html.slim +11 -0
- data/lib/generators/rolemodel/saas/devise/templates/app/views/devise/registrations/edit.html.slim +34 -0
- data/lib/generators/rolemodel/saas/devise/templates/app/views/devise/registrations/new.html.slim +17 -0
- data/lib/generators/rolemodel/saas/devise/templates/app/views/devise/sessions/new.html.slim +14 -0
- data/lib/generators/rolemodel/saas/devise/templates/app/views/devise/shared/_error_messages.html.slim +9 -0
- data/lib/generators/rolemodel/saas/devise/templates/app/views/devise/shared/_links.html.slim +14 -0
- data/lib/generators/rolemodel/saas/devise/templates/app/views/devise/unlocks/new.html.slim +11 -0
- data/lib/generators/rolemodel/saas/devise/templates/config/locales/devise.en.yml +151 -0
- data/lib/generators/rolemodel/saas/devise/templates/config/locales/devise_invitable.en.yml +31 -0
- data/lib/generators/rolemodel/saas/devise/templates/spec/factories/organizations.rb +9 -0
- data/lib/generators/rolemodel/saas/devise/templates/spec/factories/users.rb +33 -0
- data/lib/generators/rolemodel/saas/devise/templates/spec/mailers/previews/devise_mailer_preview.rb +36 -0
- data/lib/generators/rolemodel/saas/devise/templates/spec/models/user_spec.rb +29 -0
- data/lib/generators/rolemodel/saas/devise/templates/spec/support/devise.rb +8 -0
- data/lib/generators/rolemodel/saas/devise/templates/spec/system/users_spec.rb +128 -0
- data/lib/generators/rolemodel/semaphore/README.md +15 -0
- data/lib/generators/rolemodel/semaphore/USAGE +11 -0
- data/lib/generators/rolemodel/semaphore/semaphore_generator.rb +25 -0
- data/lib/generators/rolemodel/semaphore/templates/heroku-deployment-commands.sh +3 -0
- data/lib/generators/rolemodel/semaphore/templates/production-deploy.yml.erb +17 -0
- data/lib/generators/rolemodel/semaphore/templates/semaphore.yml.erb +145 -0
- data/lib/generators/rolemodel/semaphore/templates/staging-deploy.yml.erb +17 -0
- data/lib/generators/rolemodel/simple_form/README.md +10 -0
- data/lib/generators/rolemodel/simple_form/USAGE +11 -0
- data/lib/generators/rolemodel/simple_form/simple_form_generator.rb +20 -0
- data/lib/generators/rolemodel/simple_form/templates/app/inputs/collection_check_boxes_input.rb +7 -0
- data/lib/generators/rolemodel/simple_form/templates/app/inputs/collection_select_input.rb +7 -0
- data/lib/generators/rolemodel/simple_form/templates/app/inputs/grouped_collection_select_input.rb +7 -0
- data/lib/generators/rolemodel/simple_form/templates/app/inputs/segmented_control_input.rb +48 -0
- data/lib/generators/rolemodel/simple_form/templates/app/inputs/switch_checkbox_input.rb +39 -0
- data/lib/generators/rolemodel/simple_form/templates/app/inputs/tailored_select_input.rb +75 -0
- data/lib/generators/rolemodel/simple_form/templates/config/initializers/simple_form.rb +207 -0
- data/lib/generators/rolemodel/simple_form/templates/config/locales/simple_form.en.yml +31 -0
- data/lib/generators/rolemodel/simple_form/templates/lib/templates/slim/scaffold/_form.html.slim.tt +12 -0
- data/lib/generators/rolemodel/slim/README.md +9 -0
- data/lib/generators/rolemodel/slim/USAGE +5 -0
- data/lib/generators/rolemodel/slim/slim_generator.rb +24 -0
- data/lib/generators/rolemodel/slim/templates/app/views/application/_head.html.slim.tt +13 -0
- data/lib/generators/rolemodel/slim/templates/app/views/layouts/application.html.slim.tt +6 -0
- data/lib/generators/rolemodel/slim/templates/lib/templates/slim/scaffold/edit.html.slim.tt +15 -0
- data/lib/generators/rolemodel/slim/templates/lib/templates/slim/scaffold/index.html.slim.tt +13 -0
- data/lib/generators/rolemodel/slim/templates/lib/templates/slim/scaffold/new.html.slim.tt +13 -0
- data/lib/generators/rolemodel/slim/templates/lib/templates/slim/scaffold/partial.html.slim.tt +10 -0
- data/lib/generators/rolemodel/slim/templates/lib/templates/slim/scaffold/show.html.slim.tt +33 -0
- data/lib/generators/rolemodel/soft_destroyable/README.md +8 -0
- data/lib/generators/rolemodel/soft_destroyable/USAGE +9 -0
- data/lib/generators/rolemodel/soft_destroyable/soft_destroyable_generator.rb +13 -0
- data/lib/generators/rolemodel/soft_destroyable/templates/soft_destroyable.rb +82 -0
- data/lib/generators/rolemodel/soft_destroyable/templates/soft_destroyable_behavior.rb +166 -0
- data/lib/generators/rolemodel/source_map/README.md +13 -0
- data/lib/generators/rolemodel/source_map/USAGE +9 -0
- data/lib/generators/rolemodel/source_map/source_map_generator.rb +22 -0
- data/lib/generators/rolemodel/source_map/templates/lib/middleware/rolemodel/source_map.rb +45 -0
- data/lib/generators/rolemodel/source_map/templates/lib/tasks/assets.rake +43 -0
- data/lib/generators/rolemodel/tailored_select/README.md +7 -0
- data/lib/generators/rolemodel/tailored_select/USAGE +5 -0
- data/lib/generators/rolemodel/tailored_select/tailored_select_generator.rb +13 -0
- data/lib/generators/rolemodel/testing/README.md +11 -0
- data/lib/generators/rolemodel/testing/USAGE +5 -0
- data/lib/generators/rolemodel/testing/all_generator.rb +17 -0
- data/lib/generators/rolemodel/testing/factory_bot/README.md +18 -0
- data/lib/generators/rolemodel/testing/factory_bot/USAGE +8 -0
- data/lib/generators/rolemodel/testing/factory_bot/factory_bot_generator.rb +20 -0
- data/lib/generators/rolemodel/testing/factory_bot/templates/support/factory_bot.rb +3 -0
- data/lib/generators/rolemodel/testing/jasmine_playwright/README.md +9 -0
- data/lib/generators/rolemodel/testing/jasmine_playwright/jasmine_playwright_generator.rb +52 -0
- data/lib/generators/rolemodel/testing/jasmine_playwright/templates/jp-runner.config.mjs +5 -0
- data/lib/generators/rolemodel/testing/jasmine_playwright/templates/spec/javascript/browser/example_spec.js +15 -0
- data/lib/generators/rolemodel/testing/jasmine_playwright/templates/spec/javascript/browser/setupTests.js +3 -0
- data/lib/generators/rolemodel/testing/jasmine_playwright/templates/support/react.mjs +26 -0
- data/lib/generators/rolemodel/testing/parallel_tests/README.md +53 -0
- data/lib/generators/rolemodel/testing/parallel_tests/USAGE +12 -0
- data/lib/generators/rolemodel/testing/parallel_tests/parallel_tests_generator.rb +42 -0
- data/lib/generators/rolemodel/testing/rspec/README.md +46 -0
- data/lib/generators/rolemodel/testing/rspec/USAGE +14 -0
- data/lib/generators/rolemodel/testing/rspec/rspec_generator.rb +46 -0
- data/lib/generators/rolemodel/testing/rspec/templates/rails_helper.rb +72 -0
- data/lib/generators/rolemodel/testing/rspec/templates/spec_helper.rb +97 -0
- data/lib/generators/rolemodel/testing/rspec/templates/support/capybara_drivers.rb +51 -0
- data/lib/generators/rolemodel/testing/rspec/templates/support/capybara_testid.rb +5 -0
- data/lib/generators/rolemodel/testing/rspec/templates/support/helpers/action_cable_helper.rb +5 -0
- data/lib/generators/rolemodel/testing/rspec/templates/support/helpers/capybara_helper.rb +72 -0
- data/lib/generators/rolemodel/testing/rspec/templates/support/helpers/playwright_helper.rb +85 -0
- data/lib/generators/rolemodel/testing/rspec/templates/support/helpers/select_helper.rb +33 -0
- data/lib/generators/rolemodel/testing/rspec/templates/support/helpers/test_element_helper.rb +11 -0
- data/lib/generators/rolemodel/testing/rspec/templates/support/helpers.rb +12 -0
- data/lib/generators/rolemodel/testing/test_prof/README.md +5 -0
- data/lib/generators/rolemodel/testing/test_prof/USAGE +5 -0
- data/lib/generators/rolemodel/testing/test_prof/test_prof_generator.rb +14 -0
- data/lib/generators/rolemodel/testing/vitest/README.md +5 -0
- data/lib/generators/rolemodel/testing/vitest/USAGE +5 -0
- data/lib/generators/rolemodel/testing/vitest/templates/spec/javascript/example.spec.js +12 -0
- data/lib/generators/rolemodel/testing/vitest/templates/spec/javascript/test-setup.js +1 -0
- data/lib/generators/rolemodel/testing/vitest/templates/vitest.config.js +23 -0
- data/lib/generators/rolemodel/testing/vitest/vitest_generator.rb +38 -0
- data/lib/generators/rolemodel/ui_components/README.md +9 -0
- data/lib/generators/rolemodel/ui_components/USAGE +5 -0
- data/lib/generators/rolemodel/ui_components/all_generator.rb +15 -0
- data/lib/generators/rolemodel/ui_components/flash/README.md +10 -0
- data/lib/generators/rolemodel/ui_components/flash/USAGE +9 -0
- data/lib/generators/rolemodel/ui_components/flash/flash_generator.rb +22 -0
- data/lib/generators/rolemodel/ui_components/flash/templates/app/views/application/_flash.html.slim +6 -0
- data/lib/generators/rolemodel/ui_components/flash/templates/spec/support/matchers/flash_matchers.rb +19 -0
- data/lib/generators/rolemodel/ui_components/modals/README.md +119 -0
- data/lib/generators/rolemodel/ui_components/modals/USAGE +8 -0
- data/lib/generators/rolemodel/ui_components/modals/modals_generator.rb +74 -0
- data/lib/generators/rolemodel/ui_components/modals/templates/app/helpers/turbo_frame_link_helper.rb +20 -0
- data/lib/generators/rolemodel/ui_components/modals/templates/app/javascript/controllers/morph_controller.js +23 -0
- data/lib/generators/rolemodel/ui_components/modals/templates/app/javascript/controllers/toggle_controller.js +55 -0
- data/lib/generators/rolemodel/ui_components/modals/templates/app/javascript/initializers/before_morph_handler.js +21 -0
- data/lib/generators/rolemodel/ui_components/modals/templates/app/javascript/initializers/frame_missing_handler.js +12 -0
- data/lib/generators/rolemodel/ui_components/modals/templates/app/javascript/initializers/turbo_confirm.js +3 -0
- data/lib/generators/rolemodel/ui_components/modals/templates/app/views/application/_confirm.html.slim +12 -0
- data/lib/generators/rolemodel/ui_components/modals/templates/app/views/layouts/modal.html.slim.tt +26 -0
- data/lib/generators/rolemodel/ui_components/modals/templates/app/views/layouts/panel.html.slim.tt +21 -0
- data/lib/generators/rolemodel/ui_components/navbar/README.md +11 -0
- data/lib/generators/rolemodel/ui_components/navbar/USAGE +10 -0
- data/lib/generators/rolemodel/ui_components/navbar/navbar_generator.rb +54 -0
- data/lib/generators/rolemodel/ui_components/navbar/templates/app/assets/stylesheets/components/shoelace/index.scss +2 -0
- data/lib/generators/rolemodel/ui_components/navbar/templates/app/javascript/lib/shoelace.js +9 -0
- data/lib/generators/rolemodel/ui_components/navbar/templates/app/views/layouts/_navbar.html.slim +29 -0
- data/lib/generators/rolemodel/webpack/README.md +8 -0
- data/lib/generators/rolemodel/webpack/USAGE +5 -0
- data/lib/generators/rolemodel/webpack/templates/app/assets/stylesheets/application.scss +5 -0
- data/lib/generators/rolemodel/webpack/templates/app/javascript/initializers/honeybadger.js +26 -0
- data/lib/generators/rolemodel/webpack/templates/postcss.config.cjs +14 -0
- data/lib/generators/rolemodel/webpack/templates/webpack.config.js +104 -0
- data/lib/generators/rolemodel/webpack/webpack_generator.rb +76 -0
- data/lib/generators/templates/generator/%filename%.rb.tt +11 -0
- data/lib/generators/templates/generator/README.md.tt +11 -0
- data/lib/generators/templates/generator/USAGE.tt +5 -0
- data/lib/generators/templates/generator_spec/%filename%_spec.rb.tt +5 -0
- data/lib/rolemodel/engine.rb +9 -0
- data/lib/rolemodel/version.rb +5 -0
- data/lib/rolemodel-rails.rb +7 -0
- metadata +416 -0
|
@@ -0,0 +1,30 @@
|
|
|
1
|
+
{
|
|
2
|
+
"name": "<%= @project_name %>",
|
|
3
|
+
"scripts": {
|
|
4
|
+
"postdeploy": "bin/rails db:seed"
|
|
5
|
+
},
|
|
6
|
+
"env": {
|
|
7
|
+
"HONEYBADGER_API_KEY": {
|
|
8
|
+
"required": true
|
|
9
|
+
},
|
|
10
|
+
"HONEYBADGER_ENV": {
|
|
11
|
+
"required": true,
|
|
12
|
+
"value": "review-app"
|
|
13
|
+
}
|
|
14
|
+
},
|
|
15
|
+
"addons": [
|
|
16
|
+
"heroku-postgresql",
|
|
17
|
+
"papertrail"
|
|
18
|
+
],
|
|
19
|
+
"buildpacks": [
|
|
20
|
+
{
|
|
21
|
+
"url":"heroku/metrics"
|
|
22
|
+
},
|
|
23
|
+
{
|
|
24
|
+
"url": "heroku/nodejs"
|
|
25
|
+
},
|
|
26
|
+
{
|
|
27
|
+
"url": "heroku/ruby"
|
|
28
|
+
}
|
|
29
|
+
]
|
|
30
|
+
}
|
|
@@ -0,0 +1,14 @@
|
|
|
1
|
+
# Kaminari Generator
|
|
2
|
+
|
|
3
|
+
```
|
|
4
|
+
rails g rolemodel:kaminari
|
|
5
|
+
```
|
|
6
|
+
|
|
7
|
+
## Depends On
|
|
8
|
+
|
|
9
|
+
- `rolemodel:optics:base`
|
|
10
|
+
- `rolemodel:optics:icons`
|
|
11
|
+
|
|
12
|
+
## What you get
|
|
13
|
+
|
|
14
|
+
Pulls in [Kaminari](https://github.com/kaminari/kaminari) along with templates that use the Optics Pagination Component.
|
|
@@ -0,0 +1,17 @@
|
|
|
1
|
+
# frozen_string_literal: true
|
|
2
|
+
|
|
3
|
+
module Rolemodel
|
|
4
|
+
class KaminariGenerator < BaseGenerator
|
|
5
|
+
source_root File.expand_path('templates', __dir__)
|
|
6
|
+
|
|
7
|
+
def install_kaminari
|
|
8
|
+
bundle_command 'add kaminari'
|
|
9
|
+
|
|
10
|
+
generate 'kaminari:config'
|
|
11
|
+
end
|
|
12
|
+
|
|
13
|
+
def copy_templates
|
|
14
|
+
directory 'app/views/kaminari'
|
|
15
|
+
end
|
|
16
|
+
end
|
|
17
|
+
end
|
|
@@ -0,0 +1,9 @@
|
|
|
1
|
+
/ Link to the "First" page
|
|
2
|
+
- available local variables
|
|
3
|
+
url : url to the first page
|
|
4
|
+
current_page : a page object for the currently displayed page
|
|
5
|
+
total_pages : total number of pages
|
|
6
|
+
per_page : number of items to fetch per page
|
|
7
|
+
remote : data-remote
|
|
8
|
+
|
|
9
|
+
== link_to_unless current_page.first?, material_icon('first_page'), url, remote: remote, class: 'btn btn--small btn--no-border btn--icon'
|
|
@@ -0,0 +1,8 @@
|
|
|
1
|
+
/ Non-link tag that stands for skipped pages...
|
|
2
|
+
- available local variables
|
|
3
|
+
current_page : a page object for the currently displayed page
|
|
4
|
+
total_pages : total number of pages
|
|
5
|
+
per_page : number of items to fetch per page
|
|
6
|
+
remote : data-remote
|
|
7
|
+
|
|
8
|
+
.pagination__divider ...
|
|
@@ -0,0 +1,9 @@
|
|
|
1
|
+
/ Link to the "Last" page
|
|
2
|
+
- available local variables
|
|
3
|
+
url : url to the last page
|
|
4
|
+
current_page : a page object for the currently displayed page
|
|
5
|
+
total_pages : total number of pages
|
|
6
|
+
per_page : number of items to fetch per page
|
|
7
|
+
remote : data-remote
|
|
8
|
+
|
|
9
|
+
== link_to_unless current_page.last?, material_icon('last_page'), url, remote: remote, class: 'btn btn--small btn--no-border btn--icon'
|
|
@@ -0,0 +1,12 @@
|
|
|
1
|
+
/ Link to the "Next" page
|
|
2
|
+
- available local variables
|
|
3
|
+
url : url to the next page
|
|
4
|
+
current_page : a page object for the currently displayed page
|
|
5
|
+
total_pages : total number of pages
|
|
6
|
+
per_page : number of items to fetch per page
|
|
7
|
+
remote : data-remote
|
|
8
|
+
|
|
9
|
+
- unless current_page.last?
|
|
10
|
+
= link_to url, rel: 'next', remote: remote, class: 'btn btn--small btn--no-border' do
|
|
11
|
+
| Next
|
|
12
|
+
= material_icon('chevron_right')
|
|
@@ -0,0 +1,10 @@
|
|
|
1
|
+
/ Link showing page number
|
|
2
|
+
- available local variables
|
|
3
|
+
page : a page object for "this" page
|
|
4
|
+
url : url to this page
|
|
5
|
+
current_page : a page object for the currently displayed page
|
|
6
|
+
total_pages : total number of pages
|
|
7
|
+
per_page : number of items to fetch per page
|
|
8
|
+
remote : data-remote
|
|
9
|
+
|
|
10
|
+
= link_to page, url, { remote: remote, rel: page.rel, class: "btn btn--no-border btn--small #{'btn--active' if page.current? }" }
|
|
@@ -0,0 +1,19 @@
|
|
|
1
|
+
/ The container tag
|
|
2
|
+
- available local variables
|
|
3
|
+
current_page : a page object for the currently displayed page
|
|
4
|
+
total_pages : total number of pages
|
|
5
|
+
per_page : number of items to fetch per page
|
|
6
|
+
remote : data-remote
|
|
7
|
+
paginator : the paginator that renders the pagination tags inside
|
|
8
|
+
|
|
9
|
+
== paginator.render do
|
|
10
|
+
nav.pagination
|
|
11
|
+
== first_page_tag unless current_page.first?
|
|
12
|
+
== prev_page_tag unless current_page.first?
|
|
13
|
+
- each_page do |page|
|
|
14
|
+
- if page.display_tag?
|
|
15
|
+
== page_tag page
|
|
16
|
+
- elsif !page.was_truncated?
|
|
17
|
+
== gap_tag
|
|
18
|
+
== next_page_tag unless current_page.last?
|
|
19
|
+
== last_page_tag unless current_page.last?
|
|
@@ -0,0 +1,12 @@
|
|
|
1
|
+
/ Link to the "Previous" page
|
|
2
|
+
- available local variables
|
|
3
|
+
url : url to the previous page
|
|
4
|
+
current_page : a page object for the currently displayed page
|
|
5
|
+
total_pages : total number of pages
|
|
6
|
+
per_page : number of items to fetch per page
|
|
7
|
+
remote : data-remote
|
|
8
|
+
|
|
9
|
+
- unless current_page.first?
|
|
10
|
+
= link_to url, rel: 'prev', remote: remote, class: 'btn btn--small btn--no-border' do
|
|
11
|
+
= material_icon('chevron_left')
|
|
12
|
+
| Prev
|
|
@@ -0,0 +1,32 @@
|
|
|
1
|
+
# Linters Generator
|
|
2
|
+
|
|
3
|
+
## What you get
|
|
4
|
+
|
|
5
|
+
* [Rubocop](./rubocop)
|
|
6
|
+
* [ESLint](./eslint)
|
|
7
|
+
|
|
8
|
+
## Why do we use linters?
|
|
9
|
+
|
|
10
|
+
* Catches silly errors - static analysis can catch bug where code may not function in an edge case or just won't compile
|
|
11
|
+
* Teaching tool - a good linter setup is oriented around community best practices and can teach you new techniques
|
|
12
|
+
* Fast feedback loop - having feedback in your editor while working on a feature, can simplify a code review
|
|
13
|
+
* Note we **strongly** recommend that if you are using linters on a project, every project team member has it setup in their editor. No need for surprises when CI fails.
|
|
14
|
+
|
|
15
|
+
## What we care about with linters
|
|
16
|
+
|
|
17
|
+
* It is not a master to bow to
|
|
18
|
+
* You should not be reorganizing your code _just_ to get the linter to pass. For this reason we recommend turning off or lowering to warnings any line length or complexity metrics. They are hard to believe in and there will always be exceptions.
|
|
19
|
+
* If a rule doesn't match expectations of the project team, change it and document why in the config. Also consider a PR to this repo with some reasoning.
|
|
20
|
+
* Minimal set of rules
|
|
21
|
+
* We try to limit our linter config to minimum set of rules we as broader team can agree on (or commit to using).
|
|
22
|
+
* For CI we also ensure only the most severe errors cause a failing build.
|
|
23
|
+
|
|
24
|
+
### Editor Setup
|
|
25
|
+
|
|
26
|
+
* Atom
|
|
27
|
+
* [linter-rubocop](https://atom.io/packages/linter-rubocop)
|
|
28
|
+
* Supporting: [rubocop-auto-correct](https://atom.io/packages/rubocop-auto-correct)
|
|
29
|
+
* [linter-eslint](https://atom.io/packages/linter-eslint)
|
|
30
|
+
* VSCode
|
|
31
|
+
* [ruby-rubocop](https://marketplace.visualstudio.com/items?itemName=misogi.ruby-rubocop)
|
|
32
|
+
* [ESLint](https://marketplace.visualstudio.com/items?itemName=dbaeumer.vscode-eslint)
|
|
@@ -0,0 +1,14 @@
|
|
|
1
|
+
module Rolemodel
|
|
2
|
+
module Linters
|
|
3
|
+
class AllGenerator < BaseGenerator
|
|
4
|
+
source_root File.expand_path('templates', __dir__)
|
|
5
|
+
|
|
6
|
+
def run_all_the_generators
|
|
7
|
+
Dir.glob(Pathname(File.expand_path('.', __dir__)).join('*', '*generator.rb')).each do |generator|
|
|
8
|
+
name = File.basename(generator, '_generator.rb')
|
|
9
|
+
generate "rolemodel:linters:#{name}"
|
|
10
|
+
end
|
|
11
|
+
end
|
|
12
|
+
end
|
|
13
|
+
end
|
|
14
|
+
end
|
|
@@ -0,0 +1,33 @@
|
|
|
1
|
+
# frozen_string_literal: true
|
|
2
|
+
|
|
3
|
+
module Rolemodel
|
|
4
|
+
module Linters
|
|
5
|
+
class EslintGenerator < BaseGenerator
|
|
6
|
+
include ReplaceContentHelper
|
|
7
|
+
source_root File.expand_path('templates', __dir__)
|
|
8
|
+
|
|
9
|
+
ESLINT_COMMAND = "eslint 'app/**/*.js' 'spec/**/*.js'"
|
|
10
|
+
DEV_DEPENDENCIES = %w[
|
|
11
|
+
eslint
|
|
12
|
+
eslint-config-airbnb
|
|
13
|
+
eslint-plugin-import
|
|
14
|
+
eslint-import-resolver-webpack
|
|
15
|
+
eslint-plugin-jsx-a11y
|
|
16
|
+
eslint-plugin-react
|
|
17
|
+
eslint-plugin-react-hooks
|
|
18
|
+
].freeze
|
|
19
|
+
|
|
20
|
+
def install_eslint
|
|
21
|
+
run "yarn add --dev #{DEV_DEPENDENCIES.join(' ')}"
|
|
22
|
+
end
|
|
23
|
+
|
|
24
|
+
def add_config
|
|
25
|
+
template 'eslint.config.js'
|
|
26
|
+
end
|
|
27
|
+
|
|
28
|
+
def add_eslint_command_to_package_json
|
|
29
|
+
add_package_json_script 'eslint', ESLINT_COMMAND
|
|
30
|
+
end
|
|
31
|
+
end
|
|
32
|
+
end
|
|
33
|
+
end
|
|
@@ -0,0 +1,92 @@
|
|
|
1
|
+
import globals from 'globals'
|
|
2
|
+
|
|
3
|
+
export default [
|
|
4
|
+
{
|
|
5
|
+
ignores: ['app/assets/builds/**/*']
|
|
6
|
+
},
|
|
7
|
+
{ name: 'airbnb' },
|
|
8
|
+
{
|
|
9
|
+
languageOptions: {
|
|
10
|
+
parserOptions: {
|
|
11
|
+
ecmaFeatures: {
|
|
12
|
+
jsx: true
|
|
13
|
+
},
|
|
14
|
+
ecmaVersion: 'latest',
|
|
15
|
+
globals: {
|
|
16
|
+
...globals.browser,
|
|
17
|
+
...globals.es6
|
|
18
|
+
}
|
|
19
|
+
}
|
|
20
|
+
},
|
|
21
|
+
rules: {
|
|
22
|
+
'no-unused-vars': [
|
|
23
|
+
'error',
|
|
24
|
+
{
|
|
25
|
+
argsIgnorePattern: '^_', // Allow unused arguments starting with an underscore
|
|
26
|
+
varsIgnorePattern: '^_' // Allow unused variables starting with an underscore
|
|
27
|
+
}
|
|
28
|
+
],
|
|
29
|
+
|
|
30
|
+
// No semicolons
|
|
31
|
+
semi: ['error', 'never'],
|
|
32
|
+
'no-unexpected-multiline': 'error',
|
|
33
|
+
|
|
34
|
+
// 1. We follow the convention of naming "private" properties with a leading underscore
|
|
35
|
+
// 2. This conflicts with the no-unused-vars config
|
|
36
|
+
'no-underscore-dangle': 'off',
|
|
37
|
+
|
|
38
|
+
// Multiple variable declarations (without assignment) on the same line
|
|
39
|
+
// without multiple let/const
|
|
40
|
+
'one-var': ['error', { initialized: 'never', uninitialized: 'always' }],
|
|
41
|
+
'one-var-declaration-per-line': ['error', 'initializations'],
|
|
42
|
+
|
|
43
|
+
// Don't require naming all non-arrow functions. Modern browsers can usually
|
|
44
|
+
// detect the correct name if it's assigned to a variable or property.
|
|
45
|
+
'func-names': 'off',
|
|
46
|
+
|
|
47
|
+
// Don't require instance methods to use `this` (the rule name is confusing)
|
|
48
|
+
'class-methods-use-this': 'off',
|
|
49
|
+
|
|
50
|
+
// Turning this on addresses some quirks with using `var`. It's unnecessary
|
|
51
|
+
// for `let` and `const`.
|
|
52
|
+
'no-loop-func': 'off',
|
|
53
|
+
|
|
54
|
+
// Turning this on requires destructuring in too many cases
|
|
55
|
+
'prefer-destructuring': 'off',
|
|
56
|
+
|
|
57
|
+
// Turning this on prevents directly importing sub-dependencies
|
|
58
|
+
'import/no-extraneous-dependencies': 'off',
|
|
59
|
+
|
|
60
|
+
// One-liner methods can be readable without the extra spacing
|
|
61
|
+
'lines-between-class-members': ['error', 'always', { exceptAfterSingleLine: true }],
|
|
62
|
+
|
|
63
|
+
// Allow assigning to properties of arguments (might consider completely disabling this rule)
|
|
64
|
+
'no-param-reassign': ['error', { props: false }],
|
|
65
|
+
|
|
66
|
+
// Sufficiently high that it won't be too annoying
|
|
67
|
+
'max-len': ['warn', 130],
|
|
68
|
+
|
|
69
|
+
// Disabled because it complains if you mix `return` with `return <value>` in a function
|
|
70
|
+
'consistent-return': 'off',
|
|
71
|
+
|
|
72
|
+
// Allow patterns like `while ((a = getNextValue()))`
|
|
73
|
+
'no-cond-assign': ['error', 'except-parens'],
|
|
74
|
+
|
|
75
|
+
// 'import/extensions': ['warn', 'ignorePackages'],
|
|
76
|
+
|
|
77
|
+
// Default disallows mixing exponentiation with other arithmetic operators
|
|
78
|
+
'no-mixed-operators': [
|
|
79
|
+
'error',
|
|
80
|
+
{
|
|
81
|
+
allowSamePrecedence: false, // Could also make this true
|
|
82
|
+
groups: [
|
|
83
|
+
['&', '|', '^', '~', '<<', '>>', '>>>'],
|
|
84
|
+
['==', '!=', '===', '!==', '>', '>=', '<', '<='],
|
|
85
|
+
['&&', '||'],
|
|
86
|
+
['in', 'instanceof']
|
|
87
|
+
]
|
|
88
|
+
}
|
|
89
|
+
]
|
|
90
|
+
}
|
|
91
|
+
}
|
|
92
|
+
]
|
|
@@ -0,0 +1,7 @@
|
|
|
1
|
+
# Rubocop Generator
|
|
2
|
+
|
|
3
|
+
## What you get
|
|
4
|
+
|
|
5
|
+
A Rubocop installation with a standard .rubocop.yml config.
|
|
6
|
+
A custom cop that ensures form validation error responses use the correct status of `422 Unprocessable Entity`.
|
|
7
|
+
A custom cop that ensures the :chrome tag does not exist in specs.
|
|
@@ -0,0 +1,23 @@
|
|
|
1
|
+
# frozen_string_literal: true
|
|
2
|
+
|
|
3
|
+
module Rolemodel
|
|
4
|
+
module Linters
|
|
5
|
+
# Install the standard rubocop and a custom cop
|
|
6
|
+
class RubocopGenerator < BaseGenerator
|
|
7
|
+
source_root File.expand_path('templates', __dir__)
|
|
8
|
+
|
|
9
|
+
def install_rubocop
|
|
10
|
+
gem_group :development, :test do
|
|
11
|
+
gem 'rubocop'
|
|
12
|
+
gem 'rubocop-rails'
|
|
13
|
+
end
|
|
14
|
+
run_bundle
|
|
15
|
+
end
|
|
16
|
+
|
|
17
|
+
def add_config
|
|
18
|
+
copy_file '.rubocop.yml', force: true
|
|
19
|
+
directory 'lib/cops'
|
|
20
|
+
end
|
|
21
|
+
end
|
|
22
|
+
end
|
|
23
|
+
end
|
|
@@ -0,0 +1,54 @@
|
|
|
1
|
+
# frozen_string_literal: true
|
|
2
|
+
|
|
3
|
+
module Cops
|
|
4
|
+
# Custom Cop to Ensure Form Error Response Statuses
|
|
5
|
+
#
|
|
6
|
+
# There are three levels of matching here:
|
|
7
|
+
# Methods (def on_if)
|
|
8
|
+
# This scans code and only stops on the method specified.
|
|
9
|
+
# E.G. `on_if` will only move into the below checks when it encounters an if statement.
|
|
10
|
+
#
|
|
11
|
+
# Node matcher (def_node_matcher :form_error)
|
|
12
|
+
# This scans the block of code (in this case, the else branch of the if block)
|
|
13
|
+
# using AST (Abstract Tree Syntax) to match certain patterns
|
|
14
|
+
#
|
|
15
|
+
# Regex
|
|
16
|
+
# This checks the specific matching line to ensure it meets our expectations
|
|
17
|
+
class FormErrorResponse < RuboCop::Cop::Base
|
|
18
|
+
extend RuboCop::Cop::AutoCorrector
|
|
19
|
+
|
|
20
|
+
def self.rack_version
|
|
21
|
+
Gem.loaded_specs['rack'].version
|
|
22
|
+
end
|
|
23
|
+
|
|
24
|
+
def self.http_status
|
|
25
|
+
if rack_version >= '3.1'
|
|
26
|
+
:unprocessable_content
|
|
27
|
+
else
|
|
28
|
+
:unprocessable_entity
|
|
29
|
+
end
|
|
30
|
+
end
|
|
31
|
+
|
|
32
|
+
# Match code in the else branch that either: is the only line and looks like `render :something, ...`
|
|
33
|
+
# or is not the first line and looks like the same.
|
|
34
|
+
def_node_matcher :form_error, <<~PATTERN
|
|
35
|
+
{(... $(send nil? :render (:sym _) ...)) | $(send nil? :render (:sym _) ...)}
|
|
36
|
+
PATTERN
|
|
37
|
+
|
|
38
|
+
MSG = "Use status: :#{self.http_status} for invalid form requests."
|
|
39
|
+
|
|
40
|
+
# Ensure the render is returning the correct status, otherwise add the offense
|
|
41
|
+
STATUS_PAIR = /\(pair\s+\(sym :status\)\s+\(sym :#{self.http_status}\)\)/m
|
|
42
|
+
|
|
43
|
+
# Only check within if blocks
|
|
44
|
+
def on_if(node)
|
|
45
|
+
form_error(node.else_branch) do |name|
|
|
46
|
+
next if name.to_s.match?(STATUS_PAIR)
|
|
47
|
+
|
|
48
|
+
add_offense(name) do |corrector|
|
|
49
|
+
corrector.insert_after(name, ", status: :#{self.class.http_status}")
|
|
50
|
+
end
|
|
51
|
+
end
|
|
52
|
+
end
|
|
53
|
+
end
|
|
54
|
+
end
|
|
@@ -0,0 +1,45 @@
|
|
|
1
|
+
# frozen_string_literal: true
|
|
2
|
+
|
|
3
|
+
require 'rubocop'
|
|
4
|
+
|
|
5
|
+
module Cops
|
|
6
|
+
# Detect occurences of the chrome tag in specs, and warn and remove them.
|
|
7
|
+
class NoChromeTag < RuboCop::Cop::Base
|
|
8
|
+
include RuboCop::Cop::RangeHelp
|
|
9
|
+
extend RuboCop::Cop::AutoCorrector
|
|
10
|
+
|
|
11
|
+
MSG = 'The :chrome tag is only for testing, and should not be checked into the repository.'
|
|
12
|
+
RESTRICT_ON_SEND = %i[describe context it feature scenario].freeze
|
|
13
|
+
|
|
14
|
+
def on_send(node) # rubocop:disable Metrics/AbcSize,Metrics/MethodLength
|
|
15
|
+
node.arguments.each do |a|
|
|
16
|
+
if a.sym_type? && a.value == :chrome
|
|
17
|
+
range = range_with_surrounding_comma(a.source_range)
|
|
18
|
+
add_offense(range) do |corrector|
|
|
19
|
+
corrector.replace(range, '')
|
|
20
|
+
end
|
|
21
|
+
end
|
|
22
|
+
|
|
23
|
+
next unless a.hash_type?
|
|
24
|
+
|
|
25
|
+
a.pairs.each do |pair|
|
|
26
|
+
next unless pair.key.value == :chrome
|
|
27
|
+
|
|
28
|
+
range = range_with_surrounding_comma(pair.source_range)
|
|
29
|
+
add_offense(range) do |corrector|
|
|
30
|
+
corrector.replace(range, '')
|
|
31
|
+
end
|
|
32
|
+
end
|
|
33
|
+
end
|
|
34
|
+
end
|
|
35
|
+
|
|
36
|
+
def range_with_surrounding_comma(source_range)
|
|
37
|
+
buffer = source_range.source_buffer
|
|
38
|
+
src = buffer.source
|
|
39
|
+
end_pos = source_range.end_pos
|
|
40
|
+
comma_index = src[...end_pos].rindex(/\s*,\s*/)
|
|
41
|
+
|
|
42
|
+
Parser::Source::Range.new(buffer, comma_index, end_pos)
|
|
43
|
+
end
|
|
44
|
+
end
|
|
45
|
+
end
|
|
@@ -0,0 +1,10 @@
|
|
|
1
|
+
# Lograge Generator
|
|
2
|
+
|
|
3
|
+
## What you get
|
|
4
|
+
|
|
5
|
+
### Lograge
|
|
6
|
+
|
|
7
|
+
Installs [Lograge](https://github.com/roidrage/lograge).
|
|
8
|
+
|
|
9
|
+
Lograge is an opinionated gem that slims down the amount of logs that Rails generates, with the goal of reducing
|
|
10
|
+
noise that's handled by other services. For instance, it removes view rendering logs, which is a duplication of Skylight.
|
|
@@ -0,0 +1,15 @@
|
|
|
1
|
+
# frozen_string_literal: true
|
|
2
|
+
|
|
3
|
+
module Rolemodel
|
|
4
|
+
class LogrageGenerator < BaseGenerator
|
|
5
|
+
source_root File.expand_path('templates', __dir__)
|
|
6
|
+
|
|
7
|
+
def install_lograge
|
|
8
|
+
bundle_command 'add lograge'
|
|
9
|
+
end
|
|
10
|
+
|
|
11
|
+
def add_lograge_config
|
|
12
|
+
copy_file 'config/initializers/lograge.rb'
|
|
13
|
+
end
|
|
14
|
+
end
|
|
15
|
+
end
|
|
@@ -0,0 +1,16 @@
|
|
|
1
|
+
# frozen_string_literal: true
|
|
2
|
+
|
|
3
|
+
Rails.application.configure do
|
|
4
|
+
config.lograge.enabled = true
|
|
5
|
+
config.lograge.custom_payload do |controller|
|
|
6
|
+
{
|
|
7
|
+
user_id: controller.current_user.try(:id)
|
|
8
|
+
}
|
|
9
|
+
end
|
|
10
|
+
config.lograge.custom_options = lambda do |event|
|
|
11
|
+
exceptions = %w[controller action format id]
|
|
12
|
+
{
|
|
13
|
+
params: event.payload[:params].except(*exceptions)
|
|
14
|
+
}
|
|
15
|
+
end
|
|
16
|
+
end
|
|
@@ -0,0 +1,13 @@
|
|
|
1
|
+
# Mailer Generator
|
|
2
|
+
|
|
3
|
+
Depends on optics:base
|
|
4
|
+
|
|
5
|
+
## What you get
|
|
6
|
+
|
|
7
|
+
### Premailer Rails
|
|
8
|
+
|
|
9
|
+
Installs [Premailer Rails](https://github.com/fphilipe/premailer-rails)
|
|
10
|
+
|
|
11
|
+
### Email Template
|
|
12
|
+
|
|
13
|
+
This includes an example for how to user ActionMailer with Premailer Rails
|
|
@@ -0,0 +1,22 @@
|
|
|
1
|
+
Description:
|
|
2
|
+
Sets up our standard ActionMailer configuration with layout using CSS base styles
|
|
3
|
+
|
|
4
|
+
Example:
|
|
5
|
+
rails generate rolemodel:mailers
|
|
6
|
+
|
|
7
|
+
This will create:
|
|
8
|
+
app/javascript/packs/mailer_stylesheets.scss
|
|
9
|
+
app/mailers/user_mailer.rb
|
|
10
|
+
app/views/layouts/mailer.html.slim
|
|
11
|
+
app/views/user_mailer/welcome_email.html.slim
|
|
12
|
+
config/initializers/premailer_rails.rb
|
|
13
|
+
public/logo.png
|
|
14
|
+
spec/mailers/previews/user_preview.rb
|
|
15
|
+
|
|
16
|
+
This will modify:
|
|
17
|
+
config/environments/development.rb
|
|
18
|
+
config/environments/production.rb
|
|
19
|
+
|
|
20
|
+
This will remove:
|
|
21
|
+
app/views/layouts/mailer.html.erb
|
|
22
|
+
app/views/layouts/mailer.text.erb
|