The Initializer is responsible for processing the Rails configuration, such as setting the $LOAD_PATH, requiring the right frameworks, initializing logging, and more. It can be run either as a single command that‘ll just use the default configuration, like this:

  Rails::Initializer.run

But normally it‘s more interesting to pass in a custom configuration through the block running:

  Rails::Initializer.run do |config|
    config.frameworks -= [ :action_mailer ]
  end

This will use the default configuration options from Rails::Configuration, but allow for overwriting on select areas.

Methods
Attributes
[R] configuration The Configuration instance used by this Initializer instance.
[R] gems_dependencies_loaded Whether or not all the gem dependencies have been met
[R] loaded_plugins The set of loaded plugins.
Public Class methods
new(configuration)

Create a new Initializer instance that references the given Configuration instance.

     # File railties/lib/initializer.rb, line 102
102:     def initialize(configuration)
103:       @configuration = configuration
104:       @loaded_plugins = []
105:     end
run(command = :process, configuration = Configuration.new) {|configuration if block_given?| ...}

Runs the initializer. By default, this will invoke the process method, which simply executes all of the initialization routines. Alternately, you can specify explicitly which initialization routine you want:

  Rails::Initializer.run(:set_load_path)

This is useful if you only want the load path initialized, without incuring the overhead of completely loading the entire environment.

    # File railties/lib/initializer.rb, line 93
93:     def self.run(command = :process, configuration = Configuration.new)
94:       yield configuration if block_given?
95:       initializer = new configuration
96:       initializer.send(command)
97:       initializer
98:     end
Public Instance methods
add_gem_load_paths()
     # File railties/lib/initializer.rb, line 242
242:     def add_gem_load_paths
243:       unless @configuration.gems.empty?
244:         require "rubygems"
245:         @configuration.gems.each { |gem| gem.add_load_paths }
246:       end
247:     end
add_plugin_load_paths()

Adds all load paths from plugins to the global set of load paths, so that code from plugins can be required (explicitly or automatically via ActiveSupport::Dependencies).

     # File railties/lib/initializer.rb, line 238
238:     def add_plugin_load_paths
239:       plugin_loader.add_plugin_load_paths
240:     end
add_support_load_paths()

Add the load paths used by support functions such as the info controller

     # File railties/lib/initializer.rb, line 233
233:     def add_support_load_paths
234:     end
after_initialize()

Fires the user-supplied after_initialize block (Configuration#after_initialize)

     # File railties/lib/initializer.rb, line 474
474:     def after_initialize
475:       if gems_dependencies_loaded
476:         configuration.after_initialize_blocks.each do |block|
477:           block.call
478:         end
479:       end
480:     end
check_gem_dependencies()
     # File railties/lib/initializer.rb, line 253
253:     def check_gem_dependencies
254:       unloaded_gems = @configuration.gems.reject { |g| g.loaded? }
255:       if unloaded_gems.size > 0
256:         @gems_dependencies_loaded = false
257:         # don't print if the gems rake tasks are being run
258:         unless $rails_gem_installer
259:           abort "Missing these required gems:\n\#{unloaded_gems.map { |gem| \"\#{gem.name}  \#{gem.requirement}\" } * \"\\n  \"}\n\nYou're running:\nruby \#{Gem.ruby_version} at \#{Gem.ruby}\nrubygems \#{Gem::RubyGemsVersion} at \#{Gem.path * ', '}\n\nRun `rake gems:install` to install the missing gems.\n"
260:         end
261:       else
262:         @gems_dependencies_loaded = true
263:       end
264:     end
check_ruby_version()

Check for valid Ruby version This is done in an external file, so we can use it from the `rails` program as well without duplication.

     # File railties/lib/initializer.rb, line 167
167:     def check_ruby_version
168:       require 'ruby_version_check'
169:     end
initialize_cache()
     # File railties/lib/initializer.rb, line 346
346:     def initialize_cache
347:       unless defined?(RAILS_CACHE)
348:         silence_warnings { Object.const_set "RAILS_CACHE", ActiveSupport::Cache.lookup_store(configuration.cache_store) }
349:       end
350:     end
initialize_database()

This initialization routine does nothing unless :active_record is one of the frameworks to load (Configuration#frameworks). If it is, this sets the database configuration from Configuration#database_configuration and then establishes the connection.

     # File railties/lib/initializer.rb, line 339
339:     def initialize_database
340:       if configuration.frameworks.include?(:active_record)
341:         ActiveRecord::Base.configurations = configuration.database_configuration
342:         ActiveRecord::Base.establish_connection
343:       end
344:     end
initialize_dependency_mechanism()

Sets the dependency loading mechanism based on the value of Configuration#cache_classes.

     # File railties/lib/initializer.rb, line 424
424:     def initialize_dependency_mechanism
425:       ActiveSupport::Dependencies.mechanism = configuration.cache_classes ? :require : :load
426:     end
initialize_encoding()

For Ruby 1.8, this initialization sets $KCODE to ‘u’ to enable the multibyte safe operations. Plugin authors supporting other encodings should override this behaviour and set the relevant default_charset on ActionController::Base.

For Ruby 1.9, this does nothing. Specify the default encoding in the Ruby shebang line if you don‘t want UTF-8.

     # File railties/lib/initializer.rb, line 331
331:     def initialize_encoding
332:       $KCODE='u' if RUBY_VERSION < '1.9'
333:     end
initialize_framework_caches()
     # File railties/lib/initializer.rb, line 352
352:     def initialize_framework_caches
353:       if configuration.frameworks.include?(:action_controller)
354:         ActionController::Base.cache_store ||= RAILS_CACHE
355:       end
356:     end
initialize_framework_logging()

Sets the logger for Active Record, Action Controller, and Action Mailer (but only for those frameworks that are to be loaded). If the framework‘s logger is already set, it is not changed, otherwise it is set to use RAILS_DEFAULT_LOGGER.

     # File railties/lib/initializer.rb, line 395
395:     def initialize_framework_logging
396:       for framework in ([ :active_record, :action_controller, :action_mailer ] & configuration.frameworks)
397:         framework.to_s.camelize.constantize.const_get("Base").logger ||= RAILS_DEFAULT_LOGGER
398:       end
399:       
400:       RAILS_CACHE.logger ||= RAILS_DEFAULT_LOGGER
401:     end
initialize_framework_settings()

Initializes framework-specific settings for each of the loaded frameworks (Configuration#frameworks). The available settings map to the accessors on each of the corresponding Base classes.

     # File railties/lib/initializer.rb, line 460
460:     def initialize_framework_settings
461:       configuration.frameworks.each do |framework|
462:         base_class = framework.to_s.camelize.constantize.const_get("Base")
463: 
464:         configuration.send(framework).each do |setting, value|
465:           base_class.send("#{setting}=", value)
466:         end
467:       end
468:       configuration.active_support.each do |setting, value|
469:         ActiveSupport.send("#{setting}=", value)
470:       end
471:     end
initialize_framework_views()

Sets +ActionController::Base#view_paths+ and +ActionMailer::Base#template_root+ (but only for those frameworks that are to be loaded). If the framework‘s paths have already been set, it is not changed, otherwise it is set to use Configuration#view_path.

     # File railties/lib/initializer.rb, line 407
407:     def initialize_framework_views
408:       ActionMailer::Base.template_root ||= configuration.view_path  if configuration.frameworks.include?(:action_mailer)
409:       ActionController::Base.view_paths = [configuration.view_path] if configuration.frameworks.include?(:action_controller) && ActionController::Base.view_paths.empty?
410:     end
initialize_logger()

If the RAILS_DEFAULT_LOGGER constant is already set, this initialization routine does nothing. If the constant is not set, and Configuration#logger is not nil, this also does nothing. Otherwise, a new logger instance is created at Configuration#log_path, with a default log level of Configuration#log_level.

If the log could not be created, the log will be set to output to STDERR, with a log level of WARN.

     # File railties/lib/initializer.rb, line 366
366:     def initialize_logger
367:       # if the environment has explicitly defined a logger, use it
368:       return if defined?(RAILS_DEFAULT_LOGGER)
369: 
370:       unless logger = configuration.logger
371:         begin
372:           logger = ActiveSupport::BufferedLogger.new(configuration.log_path)
373:           logger.level = ActiveSupport::BufferedLogger.const_get(configuration.log_level.to_s.upcase)
374:           if configuration.environment == "production"
375:             logger.auto_flushing = false
376:             logger.set_non_blocking_io
377:           end
378:         rescue StandardError => e
379:           logger = ActiveSupport::BufferedLogger.new(STDERR)
380:           logger.level = ActiveSupport::BufferedLogger::WARN
381:           logger.warn(
382:             "Rails Error: Unable to access log file. Please ensure that #{configuration.log_path} exists and is chmod 0666. " +
383:             "The log level has been raised to WARN and the output directed to STDERR until the problem is fixed."
384:           )
385:         end
386:       end
387: 
388:       silence_warnings { Object.const_set "RAILS_DEFAULT_LOGGER", logger }
389:     end
initialize_routing()

If Action Controller is not one of the loaded frameworks (Configuration#frameworks) this does nothing. Otherwise, it loads the routing definitions and sets up loading module used to lazily load controllers (Configuration#controller_paths).

     # File railties/lib/initializer.rb, line 415
415:     def initialize_routing
416:       return unless configuration.frameworks.include?(:action_controller)
417:       ActionController::Routing.controller_paths = configuration.controller_paths
418:       ActionController::Routing::Routes.configuration_file = configuration.routes_configuration_file
419:       ActionController::Routing::Routes.reload
420:     end
initialize_temporary_session_directory()
     # File railties/lib/initializer.rb, line 434
434:     def initialize_temporary_session_directory
435:       if configuration.frameworks.include?(:action_controller)
436:         session_path = "#{configuration.root_path}/tmp/sessions/"
437:         ActionController::Base.session_options[:tmpdir] = File.exist?(session_path) ? session_path : Dir::tmpdir
438:       end
439:     end
initialize_time_zone()

Sets the default value for Time.zone, and turns on ActiveRecord::Base#time_zone_aware_attributes. If assigned value cannot be matched to a TimeZone, an exception will be raised.

     # File railties/lib/initializer.rb, line 443
443:     def initialize_time_zone
444:       if configuration.time_zone
445:         zone_default = Time.send!(:get_zone, configuration.time_zone)
446:         unless zone_default
447:           raise %{Value assigned to config.time_zone not recognized. Run "rake -D time" for a list of tasks for finding appropriate time zone names.}
448:         end
449:         Time.zone_default = zone_default
450:         if configuration.frameworks.include?(:active_record)
451:           ActiveRecord::Base.time_zone_aware_attributes = true
452:           ActiveRecord::Base.default_timezone = :utc
453:         end
454:       end
455:     end
initialize_whiny_nils()

Loads support for "whiny nil" (noisy warnings when methods are invoked on nil values) if Configuration#whiny_nils is true.

     # File railties/lib/initializer.rb, line 430
430:     def initialize_whiny_nils
431:       require('active_support/whiny_nil') if configuration.whiny_nils
432:     end
install_gem_spec_stubs()

If Rails is vendored and RubyGems is available, install stub GemSpecs for Rails, Active Support, Active Record, Action Pack, Action Mailer, and Active Resource. This allows Gem plugins to depend on Rails even when the Gem version of Rails shouldn‘t be loaded.

     # File railties/lib/initializer.rb, line 175
175:     def install_gem_spec_stubs
176:       unless Rails.respond_to?(:vendor_rails?)
177:         abort %{Your config/boot.rb is outdated: Run "rake rails:update".}
178:       end
179: 
180:       if Rails.vendor_rails?
181:         begin; require "rubygems"; rescue LoadError; return; end
182: 
183:         stubs = %w(rails activesupport activerecord actionpack actionmailer activeresource)
184:         stubs.reject! { |s| Gem.loaded_specs.key?(s) }
185: 
186:         stubs.each do |stub|
187:           Gem.loaded_specs[stub] = Gem::Specification.new do |s|
188:             s.name = stub
189:             s.version = Rails::VERSION::STRING
190:           end
191:         end
192:       end
193:     end
load_application_initializers()
     # File railties/lib/initializer.rb, line 482
482:     def load_application_initializers
483:       if gems_dependencies_loaded
484:         Dir["#{configuration.root_path}/config/initializers/**/*.rb"].sort.each do |initializer|
485:           load(initializer)
486:         end
487:       end
488:     end
load_environment()

Loads the environment specified by Configuration#environment_path, which is typically one of development, test, or production.

     # File railties/lib/initializer.rb, line 302
302:     def load_environment
303:       silence_warnings do
304:         return if @environment_loaded
305:         @environment_loaded = true
306:         
307:         config = configuration
308:         constants = self.class.constants
309:         
310:         eval(IO.read(configuration.environment_path), binding, configuration.environment_path)
311:         
312:         (self.class.constants - constants).each do |const|
313:           Object.const_set(const, self.class.const_get(const))
314:         end
315:       end
316:     end
load_gems()
     # File railties/lib/initializer.rb, line 249
249:     def load_gems
250:       @configuration.gems.each { |gem| gem.load }
251:     end
load_observers()
     # File railties/lib/initializer.rb, line 318
318:     def load_observers
319:       if gems_dependencies_loaded && configuration.frameworks.include?(:active_record)
320:         ActiveRecord::Base.instantiate_observers
321:       end
322:     end
load_plugins()

Loads all plugins in config.plugin_paths. plugin_paths defaults to vendor/plugins but may also be set to a list of paths, such as

  config.plugin_paths = ["#{RAILS_ROOT}/lib/plugins", "#{RAILS_ROOT}/vendor/plugins"]

In the default implementation, as each plugin discovered in plugin_paths is initialized:

  • its lib directory, if present, is added to the load path (immediately after the applications lib directory)
  • init.rb is evaluated, if present

After all plugins are loaded, duplicates are removed from the load path. If an array of plugin names is specified in config.plugins, only those plugins will be loaded and they plugins will be loaded in that order. Otherwise, plugins are loaded in alphabetical order.

if config.plugins ends contains :all then the named plugins will be loaded in the given order and all other plugins will be loaded in alphabetical order

     # File railties/lib/initializer.rb, line 292
292:     def load_plugins
293:       plugin_loader.load_plugins
294:     end
plugin_loader()
     # File railties/lib/initializer.rb, line 296
296:     def plugin_loader
297:       @plugin_loader ||= configuration.plugin_loader.new(self)
298:     end
prepare_dispatcher()
     # File railties/lib/initializer.rb, line 490
490:     def prepare_dispatcher
491:       require 'dispatcher' unless defined?(::Dispatcher)
492:       Dispatcher.define_dispatcher_callbacks(configuration.cache_classes)
493:       Dispatcher.new(RAILS_DEFAULT_LOGGER).send :run_callbacks, :prepare_dispatch
494:     end
process()

Sequentially step through all of the available initialization routines, in order (view execution order in source).

     # File railties/lib/initializer.rb, line 109
109:     def process
110:       Rails.configuration = configuration
111: 
112:       check_ruby_version
113:       install_gem_spec_stubs
114:       set_load_path
115:       add_gem_load_paths
116: 
117:       require_frameworks
118:       set_autoload_paths
119:       add_plugin_load_paths
120:       load_environment
121: 
122:       initialize_encoding
123:       initialize_database
124: 
125:       initialize_cache
126:       initialize_framework_caches
127: 
128:       initialize_logger
129:       initialize_framework_logging
130: 
131:       initialize_framework_views
132:       initialize_dependency_mechanism
133:       initialize_whiny_nils
134:       initialize_temporary_session_directory
135:       initialize_time_zone
136:       initialize_framework_settings
137: 
138:       add_support_load_paths
139: 
140:       load_gems
141:       load_plugins
142: 
143:       # pick up any gems that plugins depend on
144:       add_gem_load_paths
145:       load_gems
146:       check_gem_dependencies
147:       
148:       load_application_initializers
149: 
150:       # the framework is now fully initialized
151:       after_initialize
152: 
153:       # Prepare dispatcher callbacks and run 'prepare' callbacks
154:       prepare_dispatcher
155: 
156:       # Routing must be initialized after plugins to allow the former to extend the routes
157:       initialize_routing
158: 
159:       # Observers are loaded after plugins in case Observers or observed models are modified by plugins.
160:       
161:       load_observers
162:     end
require_frameworks()

Requires all frameworks specified by the Configuration#frameworks list. By default, all frameworks (Active Record, Active Support, Action Pack, Action Mailer, and Active Resource) are loaded.

     # File railties/lib/initializer.rb, line 225
225:     def require_frameworks
226:       configuration.frameworks.each { |framework| require(framework.to_s) }
227:     rescue LoadError => e
228:       # re-raise because Mongrel would swallow it
229:       raise e.to_s
230:     end
set_autoload_paths()

Set the paths from which Rails will automatically load source files, and the load_once paths.

     # File railties/lib/initializer.rb, line 205
205:     def set_autoload_paths
206:       ActiveSupport::Dependencies.load_paths = configuration.load_paths.uniq
207:       ActiveSupport::Dependencies.load_once_paths = configuration.load_once_paths.uniq
208: 
209:       extra = ActiveSupport::Dependencies.load_once_paths - ActiveSupport::Dependencies.load_paths
210:       unless extra.empty?
211:         abort "load_once_paths must be a subset of the load_paths.\nExtra items in load_once_paths: \#{extra * ','}\n"
212:       end
213: 
214:       # Freeze the arrays so future modifications will fail rather than do nothing mysteriously
215:       configuration.load_once_paths.freeze
216:     end
set_load_path()

Set the $LOAD_PATH based on the value of Configuration#load_paths. Duplicates are removed.

     # File railties/lib/initializer.rb, line 197
197:     def set_load_path
198:       load_paths = configuration.load_paths + configuration.framework_paths
199:       load_paths.reverse_each { |dir| $LOAD_PATH.unshift(dir) if File.directory?(dir) }
200:       $LOAD_PATH.uniq!
201:     end