What's the Point of Freezing Your Rails Version/Gems

What's the point of freezing your Rails version/gems?

If one of the authors of a gem you use introduce a new version of the gem, there is a possibility the new version introduces backwards incompatible changes that would break your code.

Freezing a gem puts it into the vendor folder of your application, and it will not be automatically updated on its own. Rails will use this version of the gem instead.

This allows you to update the gem on your system for other apps, while having your sole app use the version of the gem that you have always been working with, and therefore is stable.

This applies to the rails gem itself as well, as newer versions of rails might eventually cause something in your app to break, freezing it will prevent the system wide update (and, once again, allows you to update other apps on your machine, while leaving the app you freeze rails in at that version number.

Freezing gems

It's a rake task that unpacks the gems referenced in config/environment.rb into vendor/gems but his method was never very reliable and has been deprecated in favor of the new Bundler system using Gemfile.

The biggest issue with freezing gems was that compiled gems, or gems with system dependencies would never be frozen properly. Only pure-ruby gems could be properly archived.

How do I freeze gems into a Rails 3 application?

I haven't had to do this yet, but I believe it's all handled by bundler.

When you create a new rails3 app, the rails dependencies are put into your Gemfile. You can run bundle install to install them. By default, they are installed into your BUNDLE_PATH.

If you want to install them within your app, you can specify where: bundle install vendor/gems.

Why .freeze and .dup SomeGem::VERSION?

According to http://alexpeattie.com/blog/defining-versions-in-ruby-gems/, it makes the string immutable so it isn't accidentally changed.

What is the difference between rake rails:freeze:gems and rake gems:unpack?

From my understanding, gem:unpack will unpack any third party gem your app needs into vendor/gems.

rails:freeze:gems freezes only those gems having to do with rails itself, so it freezes your app to a specific version of rails. Thus the different /vendor/rails directory.

To comment a bit more:

There's this line in config/environment.rb

# Specifies gem version of Rails to use when vendor/rails is not present
RAILS_GEM_VERSION = '2.3.2' unless defined? RAILS_GEM_VERSION

So by default, rails will check to see if the vendor/rails directory exists, and use the versions of those gems if it does. If not, you must set which version of rails it will use, and rails will try to pull in the gems from your local system.

So the only difference between the two commands I see is that rails:freeze:gems dumps ONLY the rails files into vendor/rails, which is exactly where rails wants them to be.

The reason you want to use gem:unpack is to dump third party gems your application depends on, so wherever your app is run those gems won't need to be installed locally.

You can think of rails:freeze:gems as a shortcut that simply does a gem:unpack of only the rails gems into the directory rails expects (/vendor/rails), so that you don't have to manually do it. But yes, behind the scenes I expect rails:freeze:gems probably uses gem:unpack

Freezing Rails gem versions

This locks and then caches the gems into ./vendor/cache.

$ bundle package

Refer this link

How do I freeze a specific gem into a Rails 3 application?

With thanks to those who answered the question with related approaches, I ended up going with the approach mentioned in this sister question. For the sake of clarity, this is what I did:

  1. Repackage modified gem as its own gem. This takes a little finagling but is described well in the RubyGems Guides. Move said gem into your source directory (I used vendor/gems)

  2. In the project's Gemfile, point to the location of the new gem:

    gem "modified_gem", :path => "vendor/gems/modified_gem"

  3. Add new gem to version control, make sure bundle install isn't messed up with funky settings (e.g. --local), and cross your fingers.

Someone also mentioned that it's possible to mix in changes to the gem instead of overriding source files. I don't know anything more about this technique except that it should be possible.



Related Topics



Leave a reply



Submit