In today’s post I will show some optimization we can do for models. I’ll focus on how to put methods inside the right model and delegation to get a better code.
1. Put method in the right model
In our example, suppose we want to represent the animal world by creating a model Kind that represents types of animal and an Animal models representing animals.
For each type (quadrupedal, bipedal, bird) there are different animals that justify the has_many: animals relation defined in the following code.
1 2 3 4 5 6 7 8 9 10 11 12 13 | class Kind < ActiveRecord::Base |
Next, we define a method “herbivores” within the AnimalsController that, given a type of animal return all the herbivorous contained in that type.
1 2 3 4 5 6 | class AnimalsController < ApplicationController |
The flaw in this code is to have defined the method find_herbivores inside the Kind model when in fact refers to a property of the Animal class.
Let’s see how to rewrite it in proper way, using a named_scope in the Animal model.
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 | class Kind < ActiveRecord::Base |
2. Delegate
In this second example, suppose we have a Location class associated with an owner and want to show owner’s data in the Location’s view.
A first simple implementation is the following:
1 2 3 | class Location < ActiveRecord::Base |
And in the view:
1 2 3 4 | <%= @location.owner.name %> |
This type of implementation is very common in Rails applications, but you can make it more elegant by using the construct “delegate” as follows:
1 2 3 4 5 | class Location < ActiveRecord::Base |
Now we can rewrite the view as follows:
1 2 3 4 | <%= @location.owner_name %> |
The result does not change, but the code is certainly more elegant.