AdamNYC
AdamNYC

Reputation: 20415

Create temporary attribute for Rails object and pass to View

I have a Exam model, which has a database attribute score. Now, I want to have another attribute named rating, which converts this score to rating (A, B, C, D, F). I don't want to create another column for rating, so I used virtual attribute as follow:

  class Exam < ActiveRecord::Base
     attr_accessor :rating
     after_initialize :set_rating
     after_find :set_rating

     private
     def set_rating
        self.rating = case score
          when 0..49 then "F"
          when 50..79 then "B"
          else "A" 
     end
 end

This works, in the sense that I can call

e = Exam.find_by_student("John")
e.rating 

However, the object e does not have attribute rating attached to it. So if I pass object e to Rails view, I can't get e.rating where rating is an attribute.

How can I achieve what I would like, i.e., a database-less attribute that is available after_find?

Thank you.

Upvotes: 2

Views: 2893

Answers (1)

user229044
user229044

Reputation: 239291

Scrap all that and just define a method called rating.

class Exam < ActiveRecord::Base

  # ...

  def rating
    case score
      when 0..49 then "F"
      when 50..79 then "B"
      else "A" 
    end
  end

end

If you need to include this "attribute" in a JSON response, you can pass the :methods parameter to as_json to explictly include it:

render json: @exam.as_json(members: :rating)

Upvotes: 7

Related Questions