Bundler + Passenger with Rails 2.3.5? Yes, please!

17 May 2010

Bundler allows you to define the gems your application uses, resolve dependencies and load everything up. This is great, because you don’t have to manage all those different gem versions yourself any more.

There is a little problem, though. When you want to use Bundler with Rails 2.3.5. you need to do a bit of extra work. You’ll need to create a file config/preinitializer.rb that contains the following:

require "rubygems"
require "bundler"

if Gem::Version.new(Bundler::VERSION) <= Gem::Version.new("0.9.5")
  raise RuntimeError, "Your bundler version is too old." +
      "Run `gem install bundler` to upgrade."
  end

  # Set up load paths for all bundled gems
  Bundler.setup
rescue Bundler::GemNotFound
  raise RuntimeError, "Bundler couldn't find some gems." +
    "Did you run `bundle install`?"
end

Then you deploy your app with Capistrano (as root) and find that Passenger can’t find your gems. True, you need to install them, so you add a Capistrano task to run bundle install after you update your code. Still, passenger can’t find the gems.

The problem is that bundler installs the gems to your ~/.bundle. When you run bundler as root, passenger won’t be able to find the gems in /root/.bundle.

A solution is easy: bundle install .bundle will install the gems to ./.bundle, which should be your rails root directory. That solves your problem with passenger! Here’s the full Capistrano task:

desc "Install bundled gems into ./.bundle"
task :bundle do
  run "cd #{release_path}; bundle install .bundle"
end