I have been working on updating a rails application to 4.0 and spent
some
time getting to the bottom of why it wasn’t working.
What I found was, if a model has a method_missing definition then it is
called instead of any accessors. This causes any model set-up to fail.
The following example demonstrates the problem:
class Item < ActiveRecord::Base
attr_accessible :name, :content
store :content
def method_missing(id, *args)
puts “method missing: #{id}”
endend
In Rails 3.2.14:
$ rails consoleLoading development environment (Rails 3.2.14)2.0.0p247
:001 > x = Item.new(name: ‘foo’)
=> #<Item id: nil, name: “foo”, content: {}, created_at: nil,
updated_at: nil> 2.0.0p247 :002 >
and in Rails 4.0.0:
$ rails consoleLoading development environment (Rails 4.0.0)2.0.0p247
:001 > x = Item.new(name: ‘foo’)
method missing: name=
=> #<Item id: nil, name: nil, content: {}, created_at: nil, updated_at:
nil> 2.0.0p247 :002 >
In Rails 3.2.14, the name attribute is set to foo as is the intention.
In
Rails 4.0.0, however, see that method_missing is called and the
attribute
is not set.
I can work around this by manually invoking the upward method_missing
chain:
def method_missing(id, *args)
super
if respond_to? id
send(id,*args)
else
puts “method missing: #{id}”
end end
I don’t understand why this happens, or if I am doing something wrong.
Would someone with more knowledge of the internals be able to explain
this ?