From 1ff20921d3bff841bdeac326395aa29e0848ded0 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Javi=20Mart=C3=ADn?= Date: Sat, 16 Nov 2019 19:28:27 +0100 Subject: [PATCH 1/6] Daemonize puma on production We're already doing this thanks to capistrano3-puma, but it's easy to forget this option when starting puma manually. --- config/puma.rb | 1 + 1 file changed, 1 insertion(+) diff --git a/config/puma.rb b/config/puma.rb index 2389e7907..a4b30fa9d 100644 --- a/config/puma.rb +++ b/config/puma.rb @@ -13,6 +13,7 @@ state_path "#{rails_root}/tmp/pids/puma.state" stdout_redirect "#{rails_root}/log/puma_access.log", "#{rails_root}/log/puma_error.log", true bind "unix://#{rails_root}/tmp/sockets/puma.sock" +daemonize threads 0, 16 workers 2 From b0f928700026578c2005919a49a458bf359ab54d Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Javi=20Mart=C3=ADn?= Date: Sat, 16 Nov 2019 20:05:39 +0100 Subject: [PATCH 2/6] Restart the application on every reboot This way we don't have to start it manually every time the server is restarted. Note if we start the application with `bin/rails s start -e production`, as we'd probably want to do so this task doesn't depend on the server we use, the application will crash when we restart it because it will be restarted in the development environment. Maybe this issue will be fixed in future versions of Rails and/or Puma. Also note we're passing `2` workers to delayed job, and this number must be the same number we use for the `delayed_job_workers` variable in capistrano. I haven't found a way to share this variable between whenever and capistrano. --- config/schedule.rb | 6 ++++++ 1 file changed, 6 insertions(+) diff --git a/config/schedule.rb b/config/schedule.rb index 353190e5a..0c70a3ec7 100644 --- a/config/schedule.rb +++ b/config/schedule.rb @@ -39,3 +39,9 @@ end every 1.day, at: "3:00 am", roles: [:cron] do rake "votes:reset_hot_score" end + +every :reboot do + command "cd #{@path} && bundle exec puma -C config/puma/#{@environment}.rb" + # Number of workers must be kept in sync with capistrano's delayed_job_workers + command "cd #{@path} && RAILS_ENV=#{@environment} bin/delayed_job -n 2 restart" +end From dd07a863cb8b242b5c293961a332c31b35876b5f Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Javi=20Mart=C3=ADn?= Date: Sat, 16 Nov 2019 21:14:41 +0100 Subject: [PATCH 3/6] Allow restarting puma with `rails restart` So now the way to restart the application does not depend on whether we use puma or passenger. What this plugin actually does is restarting puma when we touch the `tmp/restart.txt` file, which is what `rails restart` does. --- config/puma.rb | 1 + 1 file changed, 1 insertion(+) diff --git a/config/puma.rb b/config/puma.rb index a4b30fa9d..9be47da0d 100644 --- a/config/puma.rb +++ b/config/puma.rb @@ -20,6 +20,7 @@ workers 2 preload_app! restart_command "bundle exec --keep-file-descriptors puma" +plugin :tmp_restart on_restart do puts "Refreshing Gemfile" From 69b4740ec8d0160fffd25a942094c61b2328761a Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Javi=20Mart=C3=ADn?= Date: Sun, 17 Nov 2019 14:50:34 +0100 Subject: [PATCH 4/6] Remove redundant cleanup task Capistrano automatically runs `deploy:cleanup` after finishing. --- config/deploy.rb | 2 -- 1 file changed, 2 deletions(-) diff --git a/config/deploy.rb b/config/deploy.rb index c3ebf428b..f8c4d00f7 100644 --- a/config/deploy.rb +++ b/config/deploy.rb @@ -62,8 +62,6 @@ namespace :deploy do before "deploy:restart", "setup_puma" - after :finishing, "deploy:cleanup" - desc "Deploys and runs the tasks needed to upgrade to a new release" task :upgrade do after "add_new_settings", "execute_release_tasks" From 755bc8e88a5a3e9d98b4ffde8c449d28c78ea826 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Javi=20Mart=C3=ADn?= Date: Sun, 17 Nov 2019 22:55:42 +0100 Subject: [PATCH 5/6] Restart the application on `deploy:restart` The task `deploy:restart` was doing nothing since we moved from unicorn to puma. Now we're also restarting delayed jobs on `deploy:restart`, which is probably what's expected in most cases. --- Capfile | 2 +- config/deploy.rb | 11 +++++------ 2 files changed, 6 insertions(+), 7 deletions(-) diff --git a/Capfile b/Capfile index 335828c06..e47ebb4fd 100644 --- a/Capfile +++ b/Capfile @@ -13,7 +13,7 @@ require "whenever/capistrano" require "rvm1/capistrano3" require "capistrano/puma" -install_plugin Capistrano::Puma +install_plugin Capistrano::Puma, load_hooks: false #SCM: Git require "capistrano/scm/git" diff --git a/config/deploy.rb b/config/deploy.rb index f8c4d00f7..7cd43e03f 100644 --- a/config/deploy.rb +++ b/config/deploy.rb @@ -45,8 +45,6 @@ set(:config_files, %w[ set :whenever_roles, -> { :app } namespace :deploy do - Rake::Task["puma:check"].clear_actions - after :updating, "rvm1:install:rvm" after :updating, "rvm1:install:ruby" after :updating, "install_bundler_gem" @@ -55,12 +53,13 @@ namespace :deploy do after "deploy:migrate", "add_new_settings" before :publishing, "smtp_ssl_and_delay_jobs_secrets" + after :publishing, "setup_puma" - after :publishing, "deploy:restart" - after :published, "delayed_job:restart" - after :published, "refresh_sitemap" + after :published, "deploy:restart" + before "deploy:restart", "puma:smart_restart" + before "deploy:restart", "delayed_job:restart" - before "deploy:restart", "setup_puma" + after :finished, "refresh_sitemap" desc "Deploys and runs the tasks needed to upgrade to a new release" task :upgrade do From 69be13f7a7af7295fde063b5629259f9c39a7ca1 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Javi=20Mart=C3=ADn?= Date: Tue, 19 Nov 2019 20:59:42 +0100 Subject: [PATCH 6/6] Keep default puma settings in the test environment The test environment was using the file in `config/puma.rb`, meaning it wouldn't work with Rails 5.1, which uses a different setup for Puma. I've decided to create a new file called `defaults.rb`, which will be used in every environment but development and test. We could also add an empty file in `config/puma/test.rb`; I think that's less intuitive, but it's a subjective opinion. --- config/{puma.rb => puma/defaults.rb} | 3 +-- config/puma/preproduction.rb | 2 +- config/puma/production.rb | 2 +- config/puma/staging.rb | 2 +- 4 files changed, 4 insertions(+), 5 deletions(-) rename config/{puma.rb => puma/defaults.rb} (90%) diff --git a/config/puma.rb b/config/puma/defaults.rb similarity index 90% rename from config/puma.rb rename to config/puma/defaults.rb index 9be47da0d..4f2ad945e 100644 --- a/config/puma.rb +++ b/config/puma/defaults.rb @@ -1,10 +1,9 @@ #!/usr/bin/env puma -rails_root = File.expand_path("../..", __FILE__) +rails_root = File.expand_path("../../..", __FILE__) directory rails_root rackup "#{rails_root}/config.ru" -environment "production" tag "" diff --git a/config/puma/preproduction.rb b/config/puma/preproduction.rb index 662d717be..cb965689c 100644 --- a/config/puma/preproduction.rb +++ b/config/puma/preproduction.rb @@ -1,5 +1,5 @@ #!/usr/bin/env puma -_load_from File.expand_path("../../puma.rb", __FILE__) +_load_from File.expand_path("../defaults.rb", __FILE__) environment "preproduction" diff --git a/config/puma/production.rb b/config/puma/production.rb index 7b693ef07..69d5508e3 100644 --- a/config/puma/production.rb +++ b/config/puma/production.rb @@ -1,5 +1,5 @@ #!/usr/bin/env puma -_load_from File.expand_path("../../puma.rb", __FILE__) +_load_from File.expand_path("../defaults.rb", __FILE__) environment "production" diff --git a/config/puma/staging.rb b/config/puma/staging.rb index 1097290ea..7f0321680 100644 --- a/config/puma/staging.rb +++ b/config/puma/staging.rb @@ -1,5 +1,5 @@ #!/usr/bin/env puma -_load_from File.expand_path("../../puma.rb", __FILE__) +_load_from File.expand_path("../defaults.rb", __FILE__) environment "staging"