Setup Rspec, factory bot and database cleaner for Rails 5.2.6

Let’s find out how to configure a best test suite in Rails by using Rspec framwork and the other libraries that support rspec for writing smooth tests. We will be removing rails native test folder and other configurations.

For that we will be using Rspec, Factory bot for factories, Database cleaner.

Lets start from adding these gems into our Gemfile

group :development, :test do
  # Rspec testing module and needed libs
  gem 'factory_bot_rails', '5.2.0'
  gem 'rspec-rails', '~> 4.0.0'
end

group :test do
  # db cleaner for test suite 
  gem 'database_cleaner-active_record', '~> 2.0.1'
end

Now do

bunde install # this installs all the above gems

If you have already built the Rails app, your app may contain Rails own test suite. Remove the native rails test suite to add Rspec module to your project.

We use Rspec over rails native test module because rspec provides better helpers and machnism than Rails native test.

in application.rb file comment the following line

# require 'rails/test_unit/railtie'

inside the class Application add this line:

# Don't generate system test files.
config.generators.system_tests = nil

Remove the native rails test folder:

rm -r test/

We use factories over fixtures. Remove this line from rails_helper.rb

config.fixture_path = "#{::Rails.root}/spec/fixtures"

and modify this line to:

config.use_transactional_fixtures = false # instead of true

This is for preventing rails to generate the native test files when we run rails generators.

Database Cleaner

Now we configure the database cleaner that is used for managing data in our test cycles.

Open rails_helper.rb file and require that module

require 'rspec/rails'
require 'database_cleaner'  # <= add here

Note: Use only if you run integration tests with capybara or dealing with javascript codes in the test suite.

“Capybara spins up an instance of our Rails app that can’t see our test data transaction so even tho we’ve created a user in our tests, signing in will fail because to the Capybara run instance of our app, there are no users.”

I experienced database credentials issues:

➜ rspec
An error occurred while loading ./spec/models/user_spec.rb.
Failure/Error: ActiveRecord::Migration.maintain_test_schema!

Mysql2::Error::ConnectionError:
  Access denied for user 'username'@'localhost' (using password: NO)

First I thought of using database cleaner, later I realised that this error is because of my credentials.yml.enc file was corrupted somehow. I don’t know how that happend. So try to edit and see your credentials still exists in this file.

EDITOR="code --wait" bin/rails credentials:edit

Now in the Rspec configuration block we do the Database Cleaner configuration.

Add the following file:

spec/support/database_cleaner.rb

Inside, add the following:

# DB cleaner using database cleaner library
RSpec.configure do |config|
  # This says that before the entire test suite runs, clear 
  # the test database out completely
  config.before(:suite) do
    DatabaseCleaner.strategy = :transaction
    DatabaseCleaner.clean_with(:truncation)
  end

  # This sets the default database cleaning strategy to 
  # be transactions
  config.before(:each) do
    DatabaseCleaner.strategy = :transaction
  end

  # include this if you uses capybara integration tests
  config.before(:each, :js => true) do
    DatabaseCleaner.strategy = :truncation
  end

  # These lines hook up database_cleaner around the beginning 
  # and end of each test, telling it to execute whatever 
  # cleanup strategy we selected
  config.before(:each) do
    DatabaseCleaner.start
  end

  config.after(:each) do
    DatabaseCleaner.clean
  end
end

and be sure to require this file in rails_helper.rb

require 'rspec/rails'
require 'database_cleaner'
require_relative 'support/database_cleaner'  # <= here

Configure Factories

Note: We use factories over fixtures because factories provide better features that make writing test cases an easy task.

Create a folder to generate the factories:

mkdir spec/factories

Rails generators will automatically generate factory files for models inside this folder.

A generator for model automatically creating the following files:

spec/models/model_spec.rb
spec/factories/model.rb

Now lets load Factory bot configuration to rails test suite.

Add the following file:

spec/support/factory_bot.rb

and be sure to require this file in rails_helper.rb

require 'rspec/rails'
require 'database_cleaner'
require_relative 'support/database_cleaner'
require_relative 'support/factory_bot'  # <= here

You can see the following line commented

# Dir[Rails.root.join('spec', 'support', '**', '*.rb')].sort.each { |f| require f }

You can uncomment it to make all the factories available in your test suite. But I don’t recommend that to load all the files. We will be loading each factory whenver it is necessary.

Final rails_helper.rb file. We won’t use capybara for integration tests. So we are not adding database_cleaner configuration.

# This file is copied to spec/ when you run 'rails generate rspec:install'
require 'spec_helper'
ENV['RAILS_ENV'] ||= 'test'
require File.expand_path('../config/environment', __dir__)
# Prevent database truncation if the environment is production
abort('The Rails environment is running in production mode!') if Rails.env.production?
require 'rspec/rails'
require_relative 'support/factory_bot'

# Checks for pending migrations and applies them before tests are run.
# If you are not using ActiveRecord, you can remove these lines.
begin
  ActiveRecord::Migration.maintain_test_schema!
rescue ActiveRecord::PendingMigrationError => e
  puts e.to_s.strip
  exit 1
end
RSpec.configure do |config|
  # If you're not using ActiveRecord, or you'd prefer not to run each of your
  # examples within a transaction, remove the following line or assign false
  # instead of true.
  config.use_transactional_fixtures = false

  config.infer_spec_type_from_file_location!

  # Filter lines from Rails gems in backtraces.
  config.filter_rails_from_backtrace!
  # arbitrary gems may also be filtered via:
  # config.filter_gems_from_backtrace("gem name")
end

A spec directory look something like this:

spec/
  controllers/
    user_controller_spec.rb
    product_controller_spec.rb
  factories/
    user.rb
    product.rb
  models/
    user_spec.rb
    product_spec.rb
  mailers/
    mailer_spec.rb
  services/
    service_spec.rb  
  rails_helper.rb
  spec_helper.rb

References:

https://github.com/rspec/rspec-rails
https://relishapp.com/rspec/rspec-rails/docs
https://github.com/thoughtbot/factory_bot/blob/master/GETTING_STARTED.md#configure-your-test-suite
https://github.com/DatabaseCleaner/database_cleaner

Model Specs

Lets generate a model spec. A model spec is used to test smaller parts of the system, such as classes or methods.

# RSpec also provides its own spec file generators
➜ rails generate rspec:model user
      create  spec/models/user_spec.rb
      invoke  factory_bot
      create    spec/factories/users.rb

Now run the rpsec command. That’s it. You can see the output from rspec.

➜ rspec
*

Pending: (Failures listed here are expected and do not affect your suite's status)

  1) Item add some examples to (or delete) /home/.../spec/models/user_spec.rb
     # Not yet implemented
     # ./spec/models/user_spec.rb:4

Finished in 0.00455 seconds (files took 1.06 seconds to load)
1 example, 0 failures, 1 pending

Lets discuss how to write a perfect model spec in the next lesson.

AWS SNS: How to send SMS to a topic, OTP SMS, promotional or transactional SMS

You can send SMS in 2 ways using AWS SNS.

  1. Subscribe to a topic that is already created in AWS SNS and send sms to all numbers who has the subscription.
  2. Send SMS directly to a mobile number.

You can find the following aws doc as a starting point from web and it describes how to create a topic, subscribe a topic and sending sms to the mobile numbers.

https://docs.aws.amazon.com/code-samples/latest/catalog/code-catalog-ruby-example_code-sns.html

For the demonstration purpose, I use Ruby here.

  1. Subscribe to a topic and send SMS
require 'aws-sdk-sns'  # v2: require 'aws-sdk'

sns = Aws::SNS::Resource.new(region: 'us-west-2')

topic = sns.topic('arn:aws:sns:us-west-2:123456789:MySampleTextTopic')

topic.publish({
  message: 'Hello!'
})

This assumes you already created a topic inside your aws console:

Goto AWS Console

  1. Open AWS SNS
  2. Goto Left side -> Mobile -> text messaging sms
  3. Create a topic

You can also follow the above link to perform an API to create topic, subscribe to a topic and send sms

2. Send SMS directly to a mobile number (eg: Send OTP SMS)

Either you can use aws console to send the sms or SNS API.

AWS console:

  1. Open AWS SNS
  2. Goto Left side -> Mobile -> text messaging sms
  3. We are using transactional text messages
  4. Goto publish text message
  5. Select transactional, add mobile number and publish it

Almost all cases we use an API for sending OTP SMS. For that follow the steps.

SNS API – Steps

gem install aws-sdk-sns 
require 'aws-sdk-sns'
otp = generate_otp
set_sns_client
set_sns_client_attrs
response = publish_sms(otp)
  • Generate an OTP
def generate_otp
    (1000..9999).to_a.sample
end
  • Set SNS client
def set_sns_client
    @sns_client = Aws::SNS::Client.new(
      region: ENV['AWS_SNS_REGION'],
      access_key_id: ENV['AWS_SNS_ACCESS_KEY'],
      secret_access_key: ENV['AWS_SNS_SECRET_KEY']
    )
end

  • Set SNS client attributes
 def set_sns_client_attrs
    @sns_client.set_sms_attributes({
                                     attributes: {
                                       'DefaultSenderID' => SENDER_ID,
                                       'DefaultSMSType' => SMS_TYPE
                                     }
                                   })
end

  • Publish SMS
def publish_sms(otp)
    @sns_client.publish({
                          phone_number: @mobile_no,
                          message: "#{OTM_MSG} #{otp}"
                        })
  end

Here ,

OTM_MSG: ‘Your OTP for login is’

SMS_TYPE : ‘Transactional’ or ‘Promotional’

If you want to send OTP, then it is ‘Transactional’. Else if you want to send some promotional sms of your product then it is ‘Promotional’

SENDER_ID: is the sms header that you already registered with TRAI.

The Steps to add Sender ID in AWS is given below:

For example suppose your sender id is: Zomato

Follow the steps to add our SENDER ID – Zomato to AWS SNS

  1. Sign in to the Amazon SNS console – https://console.aws.amazon.com/sns/home
  2. On the navigation panel, choose Mobile, Text messaging (SMS).
  3. On the Mobile text messaging (SMS) page, in the Text messaging preferences section, choose Edit.
  4. On the Edit text messaging preferences page, in the Details section, do the following:
  5. For Default sender ID , enter the provided sender ID to be used (Zomato) as the default for all messages from your account.
  6. Choose Save changes.

If you don’t want to register sender id, then skip this method: set_sns_client_attrs and publish the sms. It take the sms as ‘Promotional’ and sender id will be 8 character random number. Amazon use this type of sms from International route and it costs you almost $0.02 (Rs. 1.5) per sms. Very high rate. So I recommend to register any sender id that resembles your product or company name, from Jio trueconnect (that is free, link given below) and use it in SNS.

If you don’t know how to register sender id, follow this:

For AWS SNS service, there is 2 way of sending sms.

  1. Local route
  2. International route

For local route the price is Rs. 0.20 per sms
For international route the price will be Rs 1.58 per sms – too high

by default AWS SNS use International route

If you are from India follow the TRAI registration
For considering local route we have to register our use case and message templates with TRAI .

So first register here:
https://www.vilpower.in/
as an enterprise / company with all company details and our purpose

These registration requirements are designed to reduce the number of unsolicited messages that Indian consumers receive, and to protect consumers from potentially harmful messages

You can Register in Jio for free:

The link to register:
https://trueconnect.jio.com/#/home/entity-registration
Select Principal entity and continue

Recently Indian Govt made DLT Registration mandatory for sending sms.

Example:
Take Msg from AD-ZOMATO , here ZOMATO is 6 char sender id that we can give in the service provider and send sms before. But now we have to register this in DLT then only our service provider can use this.

After registering DLT we get an ENTITY ID. This entity id need to be attached in our’s otp service provider for sending otp msgs.

If you are using SNS service for the first time you should increase your SMS quota:

AWS says:

If you're new to SMS messaging with Amazon SNS, request a monthly SMS spending threshold that meets the expected demands of your SMS use case. By default, your monthly spending threshold is $1.00 (USD). You can request to increase your spending threshold in the same support case that includes your request for a sender ID

Because Amazon SNS is a distributed system, it stops sending SMS messages within minutes of the spending quota being exceeded. During this period, if you continue to send SMS messages, you might incur costs that exceed your quota.

https://docs.aws.amazon.com/sns/latest/dg/channels-sms-awssupport-sender-id.html

Requesting increases to your monthly SMS spending quota for Amazon SNS:

https://docs.aws.amazon.com/sns/latest/dg/channels-sms-awssupport-spend-threshold.html

Currently, Amazon SNS supports SMS messaging in the following AWS Regions:

https://docs.aws.amazon.com/sns/latest/dg/sns-supported-regions-countries.html

Reference:

https://docs.aws.amazon.com/sdk-for-ruby/v2/api/Aws/SNS/Client.html

Rubocop loading issue on VScode

If you are facing issue to load rubocop plugin to your VS code try the following steps to fix it.

The error message will be something like:

rubocop on VScode not working.Error “rubocop is not executable”

  1. First you have to ensure that you have installed ruby in your machine. if you are using docker containers for your project, ruby is installed inside the containers and VS Code cannot find it.
  2. Next install rubocop gem in your machine
                 $ gem install rubocop

3. Next take

  VS Code -> Settings -> search for 'rubocop' in Ruby > Rubocop: Execute Path

add the output of the following command:

        $ which rubocop

4. Reload the rubocop plugin from VS Code.

Now VS Code will get to execute rubocop.

Backup your system databases using Ruby backup gem

Install RVM (Or Rbenv) to manage your Ruby versions

 $ gpg --keyserver hkp://keys.gnupg.net --recv-keys 409B6B1796C275462A1703113804BB82D39DC0E3 7D2BAF1CF37B13E2069D6956105BD0E739499BDB
 $ curl -sSL https://get.rvm.io | bash 

Restart Terminal and type rvm -v

 $ rvm install 2.5
 $ rvm gemset create backup
 $ rvm gemset use backup
 $ gem install backup
 $ backup generate:model --trigger project_2_backup --archives --storages='s3' --compressor='gzip' --notifiers='mail' 
 Generated configuration file: '/home/ubuntu/Backup/config.rb'.
 Generated model file: '/home/ubuntu/Backup/models/project_2_backup.rb'.
 Usage:
   backup generate:model --trigger=TRIGGER
 Options:
   --trigger=TRIGGER
   [--config-path=CONFIG_PATH]  # Path to your Backup configuration directory
   [--databases=DATABASES]      # (mongodb, mysql, postgresql, redis, riak)
   [--storages=STORAGES]        # (cloudfiles, dropbox, ftp, local, ninefold, rsync, s3, scp, sftp)
   [--syncers=SYNCERS]          # (cloud_files, rsync_local, rsync_pull, rsync_push, s3)
   [--encryptors=ENCRYPTORS]    # (gpg, openssl)
   [--compressors=COMPRESSORS]  # (bzip2, gzip, lzma, pbzip2)
   [--notifiers=NOTIFIERS]      # (campfire, hipchat, mail, presently, prowl, twitter)
   [--archives]
   [--splitter]                 # use `--no-splitter` to disable
                               # Default: true 

Sample Model File

Add the following conf in Backup/models/project_2_backup.rb:

Example for mongodb

 database MongoDB do |db|
     db.name               = "db_name"
     db.username           = "db_username"
     db.password           = "db_pswd"
     db.host               = "localhost"
     db.port               = 27017 
     db.ipv6               = false
     #db.only_collections   = ["only", "these", "collections"]
     db.additional_options = ['--authenticationDatabase=admin']
     db.lock               = false
     db.oplog              = false
   end
   ## 
   # Amazon Simple Storage Service [Storage]
   #
   store_with S3 do |s3|
     # AWS Credentials
     s3.access_key_id     = "YOUR_ACCESS_KEY"
     s3.secret_access_key = "YOUR_SECRET_KEY"
     # Or, to use a IAM Profile:
     # s3.use_iam_profile = true
     s3.region            = "ap-southeast-2" 
     s3.bucket            = "bucket_name"
     s3.path              = "bucket_name_path"
     s3.keep              = 12
     # s3.keep              = Time.now - 2592000 # Remove all backups older than 1 month.
   end 

 # Notification mail infos
 notify_by Mail do |mail|
     mail.on_success           = true
     mail.on_warning           = true
     mail.on_failure           = true
     mail.from                 = "_____@gmail.com"
     mail.to                   = "____@___.com"
     mail.cc                   = "______@_____.com, _____@______.com"
     #mail.bcc                  = "bcc@email.com"
     #mail.reply_to             = "reply_to@email.com" 
     mail.address              = "smtp.gmail.com"
     mail.port                 = 587
     mail.domain               = "domain_name"
     mail.user_name            = "email_username"
     mail.password             = "email_password"
     mail.authentication       = "plain"
     mail.encryption           = :starttls
 end 

Once you’ve setup your configuration, check your work with:

$ backup check

If there are no errors, the check should report:

[2019/03/28 10:02:26][info] Configuration Check Succeeded.

Perform Backup:

$ backup perform --trigger project_2_backup

The Keep Option

keep a specified number of backups in storage. After each backup is performed, it will remove older backup package files based on the keep setting.

keep as a Number

If a number has been specified and once the keep limit has been reached, the oldest backup will be removed.

Note that if keep is set to 5, then the 6th backup will be transferred and stored, before the oldest is removed. So be sure you have space available for keep + 1 backups

keep as Time

When a Time object is set to keep it will keep backups until that time. Everything older than the set time will be removed.

A Ruby on Rails Application without models

This blog is a quick walkthrough of creating a Ruby On Rails application without a model.

Find Rails new options from here:
https://gist.github.com/abhilashak/3c0c62fa62b2f7a439c417b68d032575

Find Gemfile options from here:

http://bundler.io/v1.2/gemfile.html

Install Ruby/Rails using rbenv

$ touch .rbenv-gemsets
$ echo project-name > .rbenv-gemsets
$ rbenv gemset active
$ rbenv install 2.5.3
$ gem install bundler
$ rbenv rehash
$ gem install rails -v 5.2.9
$ rbenv rehash
$ rails new my-new-porject --skip-active-record --skip-bundle -v 5.2.9

Add in Gemfile:

ruby “2.5.3”

comment jbuilder, we don’t need it.

# gem 'jbuilder', '~> 2.8’

Move rbenv gems file to new rails app folder

$ mv .rbenv-gemsets my-new-porject

$ touch .ruby-version

$ echo 2.5.3 > .ruby-version

$ gem install bundler

$ bundle

$ ruby -v
ruby 2.5.3p105 (2018-10-18 revision 65156) [x86_64-darwin18]

Start Rails server:

$ rails s

Gemfile add:

# Bootstrap Theme

gem 'bootstrap', '~> 4.3.0’

# Slim template Engine

gem 'slim', '>=4.0.1’

Do Bundle Install

$ bundle

Rename css to scss because we use bootsrap mixins and variables that work with scss files

$ mv app/assets/stylesheets/application.css app/assets/stylesheets/application.scss

Import Bootstrap styles in app/assets/stylesheets/application.scss:

// Custom bootstrap variables must be set or imported *before* bootstrap.
@import "bootstrap";

Then, remove all the *= require and *= require_tree statements from the Sass file. Instead, use @import to import Sass files.

Bootstrap JavaScript depends on jQuery
Add jquery-rails to Gemfile:

gem 'jquery-rails', '~> 4.3.4’

Bootstrap tooltips and popovers depend on popper.js for positioning.
Add Bootstrap dependencies and Bootstrap to your application.js:

//= require jquery3
//= require popper
//= require bootstrap-sprockets

While bootstrap-sprockets provides individual Bootstrap components for ease of debugging, you may alternatively require the concatenated bootstrap for faster compilation:

//= require jquery3
//= require popper
//= require bootstrap

Sass: Individual components

All Bootstrap opponents will be imported by default.
You can also import components explicitly. To start with a full list of modules copy _bootstrap.scss file into your assets as _bootstrap-custom.scss. Then comment out components you do not want from _bootstrap-custom. In the application Sass file, replace @import ‘bootstrap’ with:

@import 'bootstrap-custom';

Your application.css:

/*
 * This is a manifest file that'll be compiled into application.css, which will include all the files
 * listed below.
 *
 * Any CSS and SCSS file within this directory, lib/assets/stylesheets, or any plugin's
 * vendor/assets/stylesheets directory can be referenced here using a relative path.
 *
 * You're free to add application-wide styles to this file and they'll appear at the bottom of the
 * compiled file so the styles you add here take precedence over styles defined in any other CSS/SCSS
 * files in this directory. Styles in this file should be added after the last require_* statement.
 * It is generally better to create a new file per style scope.
 *
 */

/*Custom bootstrap variables must be set or imported *before* bootstrap.
  The available variables can be found: 
  https://github.com/twbs/bootstrap-rubygem/blob/master/assets/stylesheets/bootstrap/_variables.scss
*/
@import "bootstrap";

Your application.js File:

// This is a manifest file that'll be compiled into application.js, which will include all the files
// listed below.
//
// Any JavaScript/Coffee file within this directory, lib/assets/javascripts, or any plugin's
// vendor/assets/javascripts directory can be referenced here using a relative path.
//
// It's not advisable to add code directly here, but if you do, it'll appear at the bottom of the
// compiled file. JavaScript code in this file should be added after the last require_* statement.
//
// Read Sprockets README (https://github.com/rails/sprockets#sprockets-directives) for details
// about supported directives.
//
//= require rails-ujs
//= require turbolinks
//= require_tree .
//= require jquery3
//= require popper
//= require bootstrap-sprockets

You can check sample bootstrap forms here:

https://bootsnipp.com/snippets/featured/login-amp-signup-forms-in-panel

Remove cable.js from javascripts # we don’t need this for now

Rbenv: Start with new ruby and rails versions

Check for the new ruby and rails versions
https://www.ruby-lang.org/en/downloads/
https://rubygems.org/gems/rails/versions

Here we are going to install Ruby – 2.4.1 & Rails – 5.1.3

Get rbenv into action
If you are not installed rbenv, you can install it from here:
https://github.com/rbenv/rbenv
After the installation make sure that, your $PATH has included rbenv/shims path. Else rbenv will not work.

1. $ rbenv install --list # Gets the list of ruby versions available

$ rbenv install 2.4.1

ruby-build: definition not found: 2.4.1

The following versions contain `2.4.1' in the name:
  rbx-2.4.1

See all available versions with `rbenv install --list'.

If the version you need is missing, try upgrading ruby-build:

  brew update && brew upgrade ruby-build

Oops..!

rbenv cannot find the version: 2.4.1

Upgrade ruby-build

Mac OSX:

$ brew upgrade ruby-build --HEAD

Now install ruby 2.4.1

$ rbenv install 2.4.1

Create a new gemset:

Rbenv gemset is a separate script and not coming with rbenv. If you are not installed this, you can install it from here:
https://github.com/jf/rbenv-gemset

$ rbenv gemset create 2.4.1 demo-app
That set up a directory for you in ~/.rbenv/versions/2.4.1/gemsets/demo-app

Set the ruby version to the newest

$ rbenv local 2.4.1

$ rbenv version
=> 2.4.1

    Activate New Gemset


For activating a gemset we need to create a .rbenv-gemsets file in the current directory.

$ touch .rbenv-gemsets
$ echo demo-app > .rbenv-gemsets

Check active gemset:

$ rbenv gemset active

Install Rails 5.1.3

$ gem install rails -v '5.1.3'
$ gem install --no-rdoc --no-ri rails -v '5.1.3' # skips the documentation

Later we can delete this .rbenv-gemsets file and add a new file named ‘.ruby-gemset’ in the rails project directory. I cannot find any other option for doing this. If anyone know more about this, please give a comment. I appreciate that.

Create a New Rails app

$ rails new demo-app

$ rm .rbenv-gemsets

$ cd demo-app
$ touch .ruby-gemset
$ echo demo-app > .ruby-gemset
$ touch .ruby-version
$ echo 2.4.1 > .ruby-version
$ rails s
=> Booting Puma
=> Rails 5.1.3 application starting in development on http://localhost:3000
=> Run `rails server -h` for more startup options
Puma starting in single mode...
* Version 3.9.1 (ruby 2.4.1-p111), codename: Private Caller
* Min threads: 5, max threads: 5
* Environment: development
* Listening on tcp://0.0.0.0:3000
Use Ctrl-C to stop

Goto http://localhost:3000/

rails-5-new.png

Done! Lets go…

Two ways to load files in Rails

There are two ways that files get loaded in Rails:

It is registered in the autoload process, and you reference a constant that corresponds to the file name. For instance, if you have app/controllers/pages_controller.rb and reference PagesController, app/controllers/pages_controller.rb will automatically be loaded. This happens for a preset list of directories in the load path. This is a feature of Rails, and is not part of the normal Ruby load process.
Files are explicitly required. If a file is required, Ruby looks through the entire list of paths in your load paths, and find the first case where the file you required is in the load path. You can see the entire load path by inspecting $LOAD_PATH (an alias for $:).

Since lib is in your load path, you have two options: either name your files with the same names as the constants, so Rails will automatically pick them up when you reference the constant in question, or explicitly require the module.

I also notice that you might be confused about another thing. ApplicationController is not the root object in the system. Observe:

module MyModule
  def im_awesome
    puts "#{self} is so awesome"
  end
end
class ApplicationController < ActionController::Base
  include MyModule
end

class AnotherClass
end

AnotherClass.new.im_awesome
# NoMethodError: undefined method `im_awesome' for #

You will need to include the module into whatever class you want to use it in.

class AnotherClass
  include MyModule
end

AnotherClass.new.im_awesome
# AnotherClass is so awesome

Of course, in order to be able to include the module in the first place, you’ll need to have it available (using either of the techniques above).

Reference: This note is from a blog/site that I looked for some knowledge.

Get information about your Rails Environment

To get information about your Rails Environment Rails, Ruby, Rack versions use the following command,

$ rake about

About your application's environment
Ruby version 1.9.2 (i686-linux)
RubyGems version 1.8.10
Rack version 1.3
Rails version 3.1.3
JavaScript Runtime therubyracer (V8)
Active Record version 3.1.3
Action Pack version 3.1.3
Active Resource version 3.1.3
Action Mailer version 3.1.3
Active Support version 3.1.3
Middleware Rack::Cache, ActionDispatch::Static, Rack::Lock, Rack::Runtime, Rack::MethodOverride, Rails::Rack::Logger, ActionDispatch::ShowExceptions, ActionDispatch::RemoteIp, Rack::Sendfile, ActionDispatch::Reloader, ActionDispatch::Callbacks, ActiveRecord::ConnectionAdapters::ConnectionManagement, ActiveRecord::QueryCache, ActionDispatch::Cookies, ActionDispatch::Session::CookieStore, ActionDispatch::Flash, ActionDispatch::ParamsParser, ActionDispatch::Head, Rack::ConditionalGet, Rack::ETag, ActionDispatch::BestStandardsSupport, Warden::Manager, OmniAuth::Builder
Application root /home/abhi/my_app
Environment development
Database adapter mysql2
Database schema version 20120704103548