Assuming the file ‘dog.rb’ exists in the load path and defines a
what will be the output of this code?
Dog.new p require 'dog.rb'
Will this raise a
Well, that depends…
Loading source files
require loads a file with the given name, and returns
If the file has already been loaded,
the method will simply return
p require 'dog.rb' #=> true p require 'dog.rb' #=> false
load works similarly, but it will reload the file and return
each time it is called. This is useful in development, where you might
want to reload a file whenever it changes.
p load 'dog.rb' #=> true p load 'dog.rb' #=> true
If a file has already been loaded with
load will reload it.
p require 'dog.rb' #=> true p load 'dog.rb' #=> true
This next example surprised me. If you
load a file and then
require will reload the file and return
true. You wouldn’t normally do this,
but I did get into trouble once when I mixed
Rails’ autoloading (more on autoloading below).
p load `dog.rb` #=> true p require `dog.rb` #=> true
require only returns
the file already appears in the
require adds an entry to
thereby preventing the second
load does not.
def dog_required? $LOADED_FEATURES.include? File.join(Dir.pwd, 'dog.rb') end p dog_required? #=> false load 'dog.rb' p dog_required? #=> false require 'dog.rb' p dog_required? #=> true
For those interested in the internals,
require in load.c.
These call the C functions
which in turn call
The function that pushes the entry into
$LOADED_FEATURES is called
rb_load_internal does not.
I played around with a branch that
adds a call to
but the tests for
Kernel#load make it
clear that is not the expected behavior.
Let’s get back to our first example. If we run this file without any other dependencies,
Dog.new will raise an error, since we refer to the
Dog constant before loading
the file that defines it.
Dog.new #=> NameError: uninitialized constant Dog
But what if this is part of a Rails application?
Rails autoloads constants based on a few naming conventions.
If ‘dog.rb’ is defined in one of the directories in the
Rails will load the file automatically when you refer to the
But will Rails
load your file, or
require it? Well that depends on the environment.
Specifically, it depends on the value of
config.cache_classes, which is normally
false in development and
true in production. This translates
loading files in development and
requireing them in production.
So what will be the output of this code?
Dog.new p require 'dog.rb'
Usually it will raise a
NameError on line 1.
But in Rails it will print
false in production
(the file will already have been
required by Rails’ autoloading system),
true in development
(the file will have been
loaded, but that does not populate
But remember, this is Ruby; it is possible that ‘dog.rb’ will redefine
class Dog end def require(filename) filename end
In this case the output of our example would be
So our example will either raise a
false, or do something else.