Automatically generate Heroku .gems file
One of the greatest parts of Heroku is that it takes care of installing your gems for you. No more /vendor/gems, missing spec files, painful upgrades, etc. In fact, no more /vendor/rails, either. A large number of gems are preinstalled for your dyno, and those are listed at http://installed-gems.heroku.com. If you have any gems not listed there, then you just have to list them in your RAILS_ROOT/.gems file:
ambethia-smtp-tls --version '>= 1.1.2' --source http://gems.github.com
mislav-will_paginate --version '>= 2.3.11' --source http://gems.github.com
thoughtbot-paperclip --version '>= 2.3.1' --source http://gems.github.com
josevalim-inherited_resources --version '>= 0.8.5' --source http://gems.github.com
justinfrench-formtastic --version '>= 0.2.2' --source http://gems.github.com
authlogic --version '>= 2.1.1'
The problem.
This can become a bit of a pain, in terms of keeping your .gems file in sync with the config.gems declarations in your environment.rb file. Luckily, Mark Dodwell posted a little rake task to produce your .gems file automatically.
The improved solution.
I’ve gone ahead and added a small improvement to that task. The version below will ping http://installed-gems.heroku.com and only write out the gems you need that aren’t already installed there. Just put this snippet into lib/tasks/heroku_gems.rake:
namespace :gems do
desc "Generate .gems file for Heroku"
task :heroku_spec => :environment do
require 'open-uri'
installed_gems = []
url = "http://installed-gems.heroku.com/"
open(url).read.scan(/<li>(\w+) [^<]*<\/li>/) do |w|
installed_gems << w.first
end
gems = Rails.configuration.gems
# output .gems
dot_gems = File.join(RAILS_ROOT, ".gems")
File.open(dot_gems, "w") do |f|
output = []
gems.each do |gem|
next if installed_gems.include?(gem.name)
spec = "#{gem.name} --version '#{gem.version_requirements.to_s}'"
spec << " --source #{gem.source}" if gem.source
output << spec
end
f.write output.join("\n")
puts output.join("\n")
end
end
end
Comments
Thanks a lot! It wasn’t a big deal to write the .gems file by hand, but this way I realized that most of what’s in /vendor didn’t make sense, especially when you have a kick-ass hosting service like Heroku.
Hi Tammer! (Great hanging out with you @ Railsconf this year by the way)
Heroku seems to be smart enough now to ignore already installed gems. Though recently it became dumber in recognizing your Rails version, which you now need to specify in .gems
I was using a standalone rake task to generate the .gems for me. Then I found a nice plugin ‘heroku_san’ by Elijah Miller with several nice heroku rake tasks. Ive updated heroku_san so it can be installed as a gem now too. No more copying .rake tasks between projects!
http://github.com/glennr/heroku_san
Leave a comment: