I'm curious as to whether it's feasible to develop a scheme for setting the default values for new ActiveRecord records. Based on some of the answers here, and this post on setting attributes, I've come up with something like this:
class Taco < ActiveRecord::Base
DEFAULT_ATTR = {spice_level: 4}
before_save do |taco|
if new_record?
DEFAULT_ATTR.each do |k,v|
taco[k] ||= v
end
end
end
end
For the paranoid, the constant could be used to also set the default in the migration:
class CreateTacos < ActiveRecord::Migration
def defaults
Taco::DEFAULT_ATTR
end
def change
add_column :tacos, :spice_level, :integer, :default => defaults[:spice_level]
end
end
What could be useful (until someone points out some obvious aspect I've overlooked!) is if this scheme was built into ActiveRecord as a callback, ala before_save (something like "new_record_defaults"). You could override the method and return a hash of symbol => default pairs, and maybe even the paranoid migration code could also leverage this.
I'm still fairly new to Rails, so I'm prepared to be told a scheme already exists or why this is a dumb idea, but feedback is welcome. :)
Update: Per Anton Grigoriev's answer, I think the attribute-defaults gem is the way to go. For posterity, here is an additional Concern, based on the author's original, for getting access to the defaults created:
module ActiveRecord
module AttributesWithDefaultsAccessor
extend ActiveSupport::Concern
def all_defaults
defaults = {}
self.private_methods.each do |method|
if method =~ /^__eval_attr_default_for_(.+)$/
defaults[$1.to_sym] = self.send(method)
end
end
defaults
end
end
class Base
include AttributesWithDefaultsAccessor
end
end