Hi
I was recently taught about the useful ActiveRecord::Base#serialize.
It’s very useful for persisting arbitrary objects through the regular
database. For example, say you want to store a Set of all the years a
Convention took place. You do:
class Convention < ActiveRecord::Base
serialize :years, Set
end
This effectively creates a Convention#years attribute, which is a set:
you can add items (years) to it, check if a certain year is contained
(included?) within, etc.
Generally wonderful. But there’s a deficiency: when you instantiate
con = Convention.new
con.years would be nil. Trying to rely in any way on con.years’ Set
properties would fail, since until you explicitly do
con.years = Set.new
the Set is simply not there. This could lead to many bugs if you
forget to assign a set to con.years. Common calls like “con.years <<
2001” and “con.years.include? 2002” would raise exceptions.
So generally, I think everyone using “serialize :foo, Set” would want
to have also:
class Convention < ActiveRecord::Base
…
def after_initialize
self.years = Set.new
end
end
Maybe there should be some automagic way to do this? Seeing that the
the after_initialize flows from the serialize call, that even looks
like a DRY violation. Also, it’s somewhat obscure: the self.years=
syntax isn’t newbie-obvious, and after_initialize doesn’t appear in
the Rails method glossary [1].
To sum up, I think there should be a feature request.
-Alder
[1] Peak Obsession