Danny
Danny

Reputation: 6025

Use regular attribute assign and save or use update_attribute?

I recently 'discovered' the update_attribute method. So, I started changing sequences like

self.attribute = "foo"; save 

in model or controller methods by

self.update_attribute(:attribute, "foo")

Now, the more I'm doing this, the more I'm wondering whether this is "good practice", and whether this method was intended to be used this way.

Any input from the "pro's" on this?

Upvotes: 1

Views: 250

Answers (2)

LucasPadovan
LucasPadovan

Reputation: 68

It's always better to use update_attribute, or update_attributes if you need to update a single instance with simple data, as you can read "UPDATE" and know that you are "UPDATING".

You must know also that there is a method called update_column, that does 'kinda' the same stuff, but, update_column does NOT update the updated_at timestamp on the database.

Also, if you need to edit a large amount of instances/rows in the database with the same value, you have a method called update_all. Here is an example

@instances = Instance.all
@instances.update_all(:attribute, value)

and that will update all the attributes of that table. You will find this usefull after doing werid migrations.

Besides all of this, you can always use the 'save' way, I strongly recomend this when you have to calculate a lot of data to update a single instance. Here is an example:

#BAD
def updater_method
    foo = Bar.first
    foo.update_attributes(attr_one: some_calcule_method, attr_two: some_other_calcule_method, attr_three: some_more_calcule_method)
end

#GOOD
def saver_method
    foo = Bar.first
    foo.attr_one = some_calcule_method
    foo.attr_two = some_other_calcule_method
    foo.attr_three = some_more_calcule_method
    etc
    foo.save!
end

This will help you in debbuging, so if any method fails, you can see it clearly, with the line number and all that stuff.

Regards, Lucas.

Upvotes: 0

Pierre-Louis Gottfrois
Pierre-Louis Gottfrois

Reputation: 17631

I would suggest using update_attribute for flags or any update operation that does not need validations since it does not fire validations. From rails documentation we can read:

Updates a single attribute and saves the record without going through the normal validation procedure. This is especially useful for boolean flags on existing records. The regular update_attribute method in Base is replaced with this when the validations module is mixed in, which it is by default.

Whereas update_attributes does:

Updates all the attributes from the passed-in Hash and saves the record. If the object is invalid, the saving will fail and false will be returned.

Let's look at the code now:

def update_attribute(name, value)
  send(name.to_s + '=', value)
  save(false)
end

def update_attributes(attributes)
  self.attributes = attributes
  save
end

Upvotes: 1

Related Questions