Rails Autoload and Ruby Require
Rails methods of locating and loading files is mostly based on convention but is built on top of Ruby's methods.
Ruby
The basic way to tell a ruby to load a file is to require it, e.g. require some_file will load some_file.rb if the file has not already been loaded. load some_file.rb will load the file (and execute any code) regardless of if the file has been loaded already.
In 1.9.2 the path that Ruby looks for these files includes:
- A number of directories in your Ruby install.
- Directories of any gems loaded
- Directories you have added to $LOAD_PATH, Rails adds a number of app directories to this variable. To see exactly what is added run puts $LOAD_PATH in both irb and a rails console.
To require a file relative to the file doing the requiring use require_relative some_directory/some_file.
Require and load both load the file when execution reaches the relevant require or load call, autoload some_file will not load the file until a module in the file is called.
Rails
In addition to adding app directories to the $LOAD_PATH, Rails loads all *.rb files in /config/initializers/ when the application starts.
Rails also has an autoload_path, If Rails comes across an uninitialized constant it will check any paths in autoload_path for a file matching the name of the constant e.g. when execution hits an unrecognized constant MyConstant it will check for a file called my_constant.rb in any paths included in autoload_paths.
The autoload_path in 3.0.7 is empty, to add the lib directory to it, add config.autoload_paths += %W(#{config.root}/lib) to config/application.rb.
If the module name does not match the file name then the file will need to be required in the normal way.
Rails also allows you to require a file with require_dependency. Require_dependency works exactly like Ruby's require except, in development mode, it reloads the file when a view is refreshed allowing you to make changes to the required file and see them by refreshing the browser.
Incude and Extend
There seems to be some confusion between require and include/extend but they are totally unrelated. Require and similar deal with loading files from the filesystem. Include and extend deal with including code from one module in another. A class the includes a module allows an instance of the class to access code from the included module. A class that extends allows the class to access code from the module called.