Home > Programming stuff, Ruby || Rails > Freaking Ruby implicit return values interferes with Rails ActiveRecord callbacks

Freaking Ruby implicit return values interferes with Rails ActiveRecord callbacks

October 25th, 2012

I just need to rant that (again) I run into a problem with unexpected side-effects of the usually neat feature of implicit return values in Ruby. This (although not really obvious) feature always returns the value of the last executed statement in a method as a return value. But this isn’t always as obvious as it sounds. This can cause strange side-effects.

As an example take the Rails callbacks for ActiveRecord. These callbacks like :before_create are typically used to handle data validation. Thus if they return ‘false’, the process to save the record is canceled.

But now instead of validation you want to ensure that certain other attributes are automatically set depending on other attributes; maybe even boolean attributes like in this block:

class Message < ActiveRecord::Base
  belongs_to :probe
  attr_accessible :probe_id, :value1, :value2, :probe_enabled

  before_create :set_probe_enabled
  
private
  def set_probe_enabled
    self.probe_enabled = self.probe.enabled?
    true # if only this would have been obvious...
  end  
end

Here we simply want to set the boolean attribute enabled? depending on the value of the enabled attribute of the associated probe. Obviously the probe.enabled? can either return true or false. Unfortunately in case of false the whole statement ‘ self.probe_enabled = self.probe.enabled?’ returns false. And if this is the last statement being executed, the whole method will return false. And a false in such a callback will cancel the creation of the object…

Take-away lesson: Pay attention to implicit return values especially in Rails ActiveRecord callback methods when dealing with boolean values.

Comments are closed.