Ruby on Rails Build a Simple Rake Task

Ruby on Rails Build a Simple Rake Task

There are many tasks that need to be performed outside of your website that are related to your web application. An example would be cleaning up temporary files. You wouldn’t want to have this code running in a web page. Fortunately rails includes a mechanism for doing this. Rake tasks make it easy to automate various aspects of your application.

First, we need to create a couple models for our sample. In this sample we will have 2 models. Our first model, Product, will store product information. Our second model, Review, will be a review of the product. Run the commands below to generate these 2 models:

1
2
3
rails g model Product name average_rating:float price:decimal{12,2} active:boolean
rails g model Review product:references user rating:integer body:text
rake db:migrate

Next, we need some seed data. Open up your seeds.rb file and add the following code:

db/seeds.rb
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
Product.delete_all
Review.delete_all

Product.create!([
  {id: 1, name: "Die Hard - Blu-Ray", price: 9.95, active: true},
  {id: 2, name: "Iron Man 3 - Blu-Ray", price: 24.95, active: true},
  {id: 3, name: "Star Trek - Into Darkness - Blu-Ray", price: 19.95, active: true},
  {id: 4, name: "The Little Mermaid - Blu-Ray", price: 29.95, active: true},
  {id: 5, name: "This is the End - Blu-Ray", price: 17.95, active: true}
])

Review.create!([
  {id: 1, product_id: 1, user: "Dan", rating: 5, body: "Epic Action Flick"},
  {id: 2, product_id: 1, user: "Will", rating: 4, body: "The Stunts were AMAZING!"},
  {id: 3, product_id: 2, user: "James", rating: 2, body: "I didn't like it as much as the first one."},
  {id: 4, product_id: 2, user: "Lisa", rating: 5, body: "Epic!"},
  {id: 5, product_id: 3, user: "Linda", rating: 5, body: "A classic revived!  Well worth watching again."},
  {id: 6, product_id: 4, user: "Kathy", rating: 5, body: "This movie is hilarious!"},
  {id: 7, product_id: 5, user: "Jim", rating: 3, body: "Really cheesy."}
])

Then run rake db:seed

1
rake db:seed

Now, lets open up the Product model so that we can add an association to reviews. Modify the Product model so that it looks like the code listed below:

app/models/product.rb
1
2
3
class Product < ActiveRecord::Base
  has_many :reviews
end

Then create a file called calculate_averages.rake in the lib/tasks folder and add the following code:

lib/tasks/calculate_averages.rake
1
2
3
4
5
6
7
8
9
10
require 'rake'

task :calculate_averages => :environment do
  products = Product.all

  products.each do |product|
    puts "Calculating average rating for #{product.name}..."
    product.update_attribute(:average_rating, product.reviews.average("rating"))
  end
end

Now, if we run our rake command we will see that the averages are updated in the database.

1
rake calculate_averages

So far so good, That’s it!!! See ya!!! :)