I really like Capistrano; it provides enough automation to my Rails apps, that I don't have to worry about gems, database migration, pre-compiling assets, restart job processors like Sidekiq, etc..
Setting up Capistrano is quite easy. It's best to have SSH access to our server via SSH keys (Github has a nice walkthrough on this). This allows running Capistrano without the need to input the password. I also setup the server's SSH keys in my source control server, in my case Bitbucket for git (I use Digital Ocean as server host).
Gemfile
Let's start by adding the necessary gems to our app's Gemfile.
group :development do
gem 'capistrano', require: false
gem 'capistrano-rails'
gem 'capistrano-bundler'
gem 'capistrano-rvm'
end
We use rvm to manage the Ruby versions in the server, hence the capistrano-rvm gem.
Update gems by running:
bundle
Then install Capistrano by running the command:
cap install .
This creates a few files for us, starting with the Capfile.
Capfile
Here we load any functionality we need for our deployment:
# Capfile
# Load DSL and set up stages
require 'capistrano/setup'
require 'capistrano/deploy'
require 'capistrano/rvm'
require 'capistrano/bundler'
require 'capistrano/rails/assets'
require 'capistrano/rails/migrations'
# Load custom tasks from `lib/capistrano/tasks' if you have any defined
Dir.glob('lib/capistrano/tasks/*.rake').each { |r| import r }
Please note that capistrano/bundler will take care of bundling our gems in the server, and isolating them; capistrano/rails/assets will pre-compile the assets; and capistrano/rails/migrations will run the migrations.
Deploy
Another file that Capistrano generates for us is config/deploy.rb
. For our basic deployment it sets the following options:
set :application, '[APPLICATION NAME]'
set :format, :pretty
set :log_level, :debug
set :pty, true
set :linked_files, %w{config/database.yml}
set :linked_dirs, %w{bin log tmp/pids tmp/cache tmp/sockets vendor/bundle public/system}
set :keep_releases, 3
set :rails_env, 'production'
set :repo_url, '[GIT REPO URL]'
set :scm, :git
set :branch, 'master'
The linked files are usually secure files we don't hold into our source control (e.g. git). database.yml is such a file, so we need to create that manually in the server. In fact if we run deploy:check now, Capistrano will tell us where to add the database.yml file:
cap production deploy:check
Every time we run the cap
command, we must specify the deployment stage, e.g. staging or production. Capistrano creates files for each of them inside config/deploy
folder. The production.rb
file could look like this (replace the square braces with your own settings):
set :stage, :production
set :deploy_to, '[SERVER DIRECTORY]'
server '[SERVER IP ADDRESS/URL]', user: '[SERVER USER]', roles: %w{web app db}
If the deploy:check command runs without problem, we can finally deploy our app to the server:
cap production deploy
We may need to fix any errors that this command will return, in my experience, mostly due to security settings.
Conclusion
We walked through a basic Rails app deployment with Capistrano. But Capistrano can do much, much more, such as setting up/restarting the web server (e.g. nginx), monitoring system (e.g. monit), queue processor (e.g. Sidekiq), etc..
Happy deployment!