ActiveModel::Errors inherits from hash and behaves unexpectedly

Posted Over 11 years ago. Visible to the public.

ActiveModel::Errors is used to handle validation errors on Rails objects. If you inspect an instance, it feels like a hash (to be more precise, it inherits from Hash):

errors = ActiveModel::Errors.new(Object.new)
=> {}
>> 
?> errors.add(:base, "foo")
=> ["foo"]
>> errors.add(:base, "bar")
=> ["foo", "bar"]
>> 
?> errors
=> {:base=>["foo", "bar"]}

If you need to hack anything with these errors, beware that it behaves in a special way. If you iterate over the errors it will decompose arrays.
For attributes with multiple errors such as :base => ["foo", "bar"] it yields once per value ("foo" and "bar" here) within the array and not per key.

>> for k,v in errors do
>>   puts k
>>   puts v
>>   puts "--"
>> end

base
foo
--
base
bar
--

In contrast, a hash simply yields once per key giving you only the array as value.

Thomas Eisenbarth
Last edit
Over 11 years ago
License
Source code in this card is licensed under the MIT License.
Posted by Thomas Eisenbarth to makandra dev (2012-10-23 17:14)