You add a new gem to your Gemfile and start using it in your application’s code. You never have to do ‘require <gemname>’ to use it in the application.
Ever wondered how rails autoloads all your gems? Let me walk you through the process which rails follow. Actually Rails uses Bundler to handle dependency management of all the gems and also autoload them.
How Rails put the gems “on the load path”?
[app]/config/boot.rb
1 2 3 4 5 6 |
require 'rubygems' # Set up gems listed in the Gemfile. ENV['BUNDLE_GEMFILE'] ||= File.expand_path('../../Gemfile', __FILE__) require 'bundler/setup' if File.exists?(ENV['BUNDLE_GEMFILE']) |
The file is loaded during the rails initialization process and all it does is load rubygems and run Bundler. This will automatically discover your Gemfile and puts all the gems listed in the load path so that they can be required later. (Note: The gem’s aren’t run at this point, just the load paths are set.)
How are gems required (run) ?
[app]/config/application.rb
1 2 3 4 5 6 7 |
if defined?(Bundler) # If you precompile assets before deploying to production, use this line Bundler.require(*Rails.groups(:assets => %w(development test))) # If you want your assets lazily compiled in production, use this line # Bundler.require(:default, :assets, Rails.env) end |
This file includes all the gems listed in the application’s Gemfile by calling Bundler.require. Bundler allows us to specify which groups to automatically require through the parameters to Bundler.require
The above code loads the assets group of gems only in development and test environments. It makes sense as we use precompiled assets in production, hence assets gems aren’t required to be loaded. (see Rails.groups). There are few comments in the file which will help you to change the default behavior if required.
Understanding rails initialization internals allows us to tweak the process to reduce the application load time. We’ll talk more about the process in the coming posts.