Using Capistrano
For most programmers, deployment is an area that could do with a touch of laziness. Deploying to a cluster—or even one machine—can be repetitive and tiring. Enter Capistrano, a Ruby deployment tool that makes the task of deploying an application to servers easier by running defined tasks for you on the remote servers.
The Ruby programmers' toolbox contains so many tools for eliminating most of their work, it's fair to say that Ruby programmers are probably some of the laziest. If having all the boring jobs done for you isn't enough, Ruby programmers even contrive to have most of their tools built in one language—Ruby. No bash-make-PHP-Perl combinations. It's all Ruby.
Think of Capistrano as a build system that specializes in running commands remotely on any number of machines. If you have to connect to a half-dozen machines to push updates, or have no quick-and-easy way of rolling back the entire cluster if (or when?) something goes wrong, you need to be a little more lazy.
Capistrano groups tasks in recipes, and the default recipe, which we'll look at in a moment, is very geared toward Rails, running migrations and restarting the Rails server. However, Capistrano's core is not Rails-specific. You can build your own recipes for all your dullest tasks, and you can tweak the Rails recipe to work with whichever language or framework you're using.
Let's take a look at what Capistrano does for Rails deployment, how to build your own tasks and how to push your own application out to 20 servers with just one command.
Like Rails, Capistrano increasingly is deployed with flavours of Linux and is installed by default in Leopard, so you might not even have to install it. If you do need to, installing Capistrano is as easy as any Ruby gem. Simply run:
sudo gem install -y capistrano
Capistrano has two main commands: cap, which is used for viewing and running the tasks, and capify, which is used to set up a Rails project for use with Capistrano. Assuming you have a Rails project, grab a copy of it, and run capify at the project root:
cd path/to/project capify .
This creates just two files: Capfile and config/deploy.rb. Capfile is to Capistrano as Makefile is to make and Rakefile is to rake. Capistrano expects a Capfile to be present and to contain the tasks or to include a Ruby file that does.
In this case, the Capfile just includes config/deploy.rb, so the latter is the one of interest. The deploy file contains a bunch of settings you need to take care of before running cap, starting with:
set :application, "set your application name here" set :repository, "set your repository location here"
If you aren't used to Ruby's syntax, this all will look deceptively like simple configuration. However, because you don't have to use brackets when calling functions in Ruby, each line actually is a call to the set() function in Capistrano's core:
set(:application, "your-app-name")
Set the :application variable to a name without spaces—this will be used to create a deployment directory later. Set :repository to your versioning repository's URL (in this example, we use SVN).
If you have a user name and password for SVN, set them with the lines:
set :scm_username, "svn-username" set :scm_password, "svn-password"
Then, uncomment and set the deployment directory. If the deploy_to doesn't exist on your deployment server, Capistrano creates it:
set :deploy_to, "/path/to/doc/root/www/#{application}"
Here, we're using the application variable we set previously to set part of the deploy_to variable. This is all standard Ruby syntax, available in all Capistrano scripts, making this way of working extremely powerful and a little less cumbersome than a hodge-podge of obscure syntaxes.
Finally, we need to set the servers that will host the deployment. You can add as many servers as you like, and the server name just has to be something that SSH understands—for example:
role :app, "app-server-1", "app-server-2", "app-server-3" role :web, "192.168.1.123" role :db, "db-server-1", :primary => true
If you're just testing out Capistrano, it's worth setting the deployment location as your working machine; that way, you can learn without moving between machines:
role :app, "me@my-local-ip"
Now we're ready to ask Capistrano to set up the deployment location using the command:
cap deploy:setup
When you run this, Capistrano starts showing you what it's doing. This helps when debugging Capfiles, and it reassures you that you're doing the right thing. Whenever you connect to another server, you'll be prompted for the password, as usual, after which Capistrano will run a bunch of other commands.
After deploy:setup, the deployment directory now contains some extra directories that will allow cap to push new versions, do rollbacks and so on:
myapp/
releases/ shared/log shared/pids shared/system
Next, we get on and deploy the application. Capistrano will check out the source, put it into releases and create a symlink to it called current:
cap deploy:cold
After this has run, take another look in the deployment location:
# current@ -> /www/captest/myapp/releases/20080614144520
This a “cold” deployment, meaning tasks that are one-time tasks are run. To deploy the application in the future, you simply use the deploy task:
cap deploy
When you've run either deploy:cold or deploy, have a look in the deployment directory and find where your source code fits into Capistrano's way of deploying things.
The deploy task replaces logging in to the server, getting the source, setting up any databases and restarting the servers. Run it a few times, and get used to that lazy feeling!
Realizing the promise of Apache® Hadoop® requires the effective deployment of compute, memory, storage and networking to achieve optimal results. With its flexibility and multitude of options, it is easy to over or under provision the server infrastructure, resulting in poor performance and high TCO. Join us for an in depth, technical discussion with industry experts from leading Hadoop and server companies who will provide insights into the key considerations for designing and deploying an optimal Hadoop cluster.
Sponsored by AMD
Built-in forensics, incident response, and security with Red Hat Enterprise Linux 6
Every security policy provides guidance and requirements for ensuring adequate protection of information and data, as well as high-level technical and administrative security requirements for a system in a given environment. Traditionally, providing security for a system focuses on the confidentiality of the information on it. However, protecting the data integrity and system and data availability is just as important. For example, when processing United States intelligence information, there are three attributes that require protection: confidentiality, integrity, and availability.
Learn more about catching the bad guy in this free white paper.
Sponsored by DLT Solutions
| Designing Electronics with Linux | May 22, 2013 |
| Dynamic DNS—an Object Lesson in Problem Solving | May 21, 2013 |
| Using Salt Stack and Vagrant for Drupal Development | May 20, 2013 |
| Making Linux and Android Get Along (It's Not as Hard as It Sounds) | May 16, 2013 |
| Drupal Is a Framework: Why Everyone Needs to Understand This | May 15, 2013 |
| Home, My Backup Data Center | May 13, 2013 |
- New Products
- Linux Systems Administrator
- Senior Perl Developer
- Technical Support Rep
- UX Designer
- Web & UI Developer (JavaScript & j Query)
- Designing Electronics with Linux
- Dynamic DNS—an Object Lesson in Problem Solving
- Making Linux and Android Get Along (It's Not as Hard as It Sounds)
- Using Salt Stack and Vagrant for Drupal Development
- Reply to comment | Linux Journal
6 hours 54 min ago - Nice article, thanks for the
17 hours 34 min ago - I once had a better way I
23 hours 20 min ago - Not only you I too assumed
23 hours 38 min ago - another very interesting
1 day 1 hour ago - Reply to comment | Linux Journal
1 day 3 hours ago - Reply to comment | Linux Journal
1 day 10 hours ago - Reply to comment | Linux Journal
1 day 10 hours ago - Favorite (and easily brute-forced) pw's
1 day 12 hours ago - Have you tried Boxen? It's a
1 day 18 hours ago
Enter to Win an Adafruit Pi Cobbler Breakout Kit for Raspberry Pi

It's Raspberry Pi month at Linux Journal. Each week in May, Adafruit will be giving away a Pi-related prize to a lucky, randomly drawn LJ reader. Winners will be announced weekly.
Fill out the fields below to enter to win this week's prize-- a Pi Cobbler Breakout Kit for Raspberry Pi.
Congratulations to our winners so far:
- 5-8-13, Pi Starter Pack: Jack Davis
- 5-15-13, Pi Model B 512MB RAM: Patrick Dunn
- 5-21-13, Prototyping Pi Plate Kit: Philip Kirby
- Next winner announced on 5-27-13!
Featured Jobs
| Linux Systems Administrator | Houston and Austin, Texas | Host Gator |
| Senior Perl Developer | Austin, Texas | Host Gator |
| Technical Support Rep | Houston and Austin, Texas | Host Gator |
| UX Designer | Austin, Texas | Host Gator |
| Web & UI Developer (JavaScript & j Query) | Austin, Texas | Host Gator |
Free Webinar: Hadoop
How to Build an Optimal Hadoop Cluster to Store and Maintain Unlimited Amounts of Data Using Microservers
Realizing the promise of Apache® Hadoop® requires the effective deployment of compute, memory, storage and networking to achieve optimal results. With its flexibility and multitude of options, it is easy to over or under provision the server infrastructure, resulting in poor performance and high TCO. Join us for an in depth, technical discussion with industry experts from leading Hadoop and server companies who will provide insights into the key considerations for designing and deploying an optimal Hadoop cluster.
Some of key questions to be discussed are:
- What is the “typical” Hadoop cluster and what should be installed on the different machine types?
- Why should you consider the typical workload patterns when making your hardware decisions?
- Are all microservers created equal for Hadoop deployments?
- How do I plan for expansion if I require more compute, memory, storage or networking?




Comments
cap'ing Rails projects on servers
Hi Dan,
nice article - do you have any 'advanced' setups, like this one?
role :app, "10.4.3.223", :primary => true, :user => "root"
role :web, "10.4.3.221"
role :db, "10.4.3.220"
set :gateway, "webserver.domain.tld"
set :repository, "git@10.4.3.222:#{application}.git"
why?
Because I cannot get my multistage deploy to work :)
All the blogs and articles I've come around, they all seem to focus on setups with all servers on one machine, and git somewhere entirely else (like github.com)
Best regards,
Walther