The ELC Community Blog
A knowledge exchange on Ruby on Rails and Agile Development
ActiveRecord attribute update semantics
by Ryan Garver on February 20, 2007
ActiveRecord (AR) provides a number of great features. One feature that is often taken for granted is the mapping of table columns (attributes) to class signals. We use this feature of AR without thinking about it.
1 article = Article.find(1)
2 article.attributes[:title] #=> "A Blog Posting"
3 article.title #=> "A Blog Posting"
We also can take this several steps further and modify how AR responds to requests for the value of a attribute. Jamis Buck had a recent blog post outlining an interesting way to set up default values for an attribute than can depend on another attribute. The difficulty in AR comes when you need to modify what happens when attributes are being updated. A great example of this is if you want an action to always happen when (say) you assign an to 1 Author
. AR has several different ways of getting and setting attributes out of the database. We'll focus on the setting since that is often the confusing part of AR hacking. You should pay attention to the underlying implementation mentioned below; it's easy to accidentally create infinite recursion. 1 Article.author
1 article.attributes[:attr_name]=value
- Every AR object has an
Hash that contains the1 attributespairs that correspond to the columns and their values for the object. This Hash is bi-directional and therefore can be modified. Once the1 name=>valueHash has been updated you can save the AR object and those updates will persist. Much of the alternative methods of updating AR objects are built on this base. The1 attributescan be either a string or a symbol.1 attr_name 1 article.attr_name=value
- This assigns
with1 attr_namewithin the in-memory AR object. To commit the change you must call1 valueon the AR object. This ends up calling1 saveunder the hood. When overwriting how the attributes are updated in a AR object you'll want to override this method and do the final assignment using1 []=
.1 []=
1 article.update_attribute(:attr_name, value)
- This assigns the
to1 valueand saves the value to the database all in one go. Behind the scene this calls the1 attr_nameto do the assignment which means that you can override how this assignment takes place. This method of assignment also skips validation on the attribute.1 article.attr_name=
1 article.update_attributes(:attr_name1 => value1, :attr_name2 => value2, ...)
- This method is the same as calling
for each1 []=
pair and then saving.1 name=>value
A quick note. When overloading the assignment of association do not try to do the overloading on (for example) the method, but rather the 1 author=
method. Otherwise you confuse AR and it doesn't call your methods. 1 author_id=
Timeline
- Liquid Filter Extensions
- Using and Testing Rails with Multiple Databases
- Securing your Models
- Installing RMagick properly in OSX
- RubyGems 0.91 and the "refresh" error
- ActiveRecord attribute update semantics
- Installing Webmin on Ec2
- Interactive Capistrano deploys
- Ruby on Rails on EC2
- Upgrade EC2 FC4/Base to FC5
- Beating The Browser's Iframe Security
Comments