We spent a big chunk of yesterday hunting down a strange bug in one of
our rails apps and created a test project to try out different theories
on what was going on. The result so far is a very small test case app
that perfectly reproduces the problem. The question is, is there
anything wrong with what we’re doing here, or is it a problem with
ActiveRecord? We’re on rails 1.1.6 at the moment, so if this is a known
bug that’s fixed in 1.2, just club me over the head with the trac
reference.
Given the following two models…
class Gadget < ActiveRecord::Base
has_one :widget
end
class Widget < ActiveRecord::Base
belongs_to :gadget
def save
gadget.save
super
end
end
and the following test…
class WidgetTest < Test::Unit::TestCase
fixtures :widgets, :gadgets
Replace this with your real tests.
def test_update
w = Widget.find(1)
assert_equal(w,w.gadget.widget)
w.save
end
end
Obviously this is a contrived example (why would anyone every want to
call w.gadget.widget?). However, it’s a greatly boiled down version of
our problem app that has many models and a long series of methods
calling each other from different models. Calling w.gadget.widget in
this example doesn’t make any sense, however, to the best of my
knowledge it’s not illegal either.
Given the above, if I comment out either the ‘gadget.save’ line in
widget.rb, or the ‘… w.gadget.widget)’ assert line in the test,
the test runs successfully. However, with both lines left in place, we
get the following error from deep within the bowels of ActiveRecord.
So, my question is, is there a Rails bug here, or are we doing something
fundamentally inappropriate?
- Error:
test_update(WidgetTest):
ArgumentError: wrong number of arguments (1 for 0)
/usr/lib/ruby/gems/1.8/gems/activerecord-1.14.4/lib/active_record/associations/association_proxy.rb:110:in
`save’
/usr/lib/ruby/gems/1.8/gems/activerecord-1.14.4/lib/active_record/associations/association_proxy.rb:110:in
`send’
/usr/lib/ruby/gems/1.8/gems/activerecord-1.14.4/lib/active_record/associations/association_proxy.rb:110:in
`method_missing’
/usr/lib/ruby/gems/1.8/gems/activerecord-1.14.4/lib/active_record/callbacks.rb:349:in
`callback’
/usr/lib/ruby/gems/1.8/gems/activerecord-1.14.4/lib/active_record/callbacks.rb:346:in
`callback’
/usr/lib/ruby/gems/1.8/gems/activerecord-1.14.4/lib/active_record/callbacks.rb:341:in
`each’
/usr/lib/ruby/gems/1.8/gems/activerecord-1.14.4/lib/active_record/callbacks.rb:341:in
`callback’
/usr/lib/ruby/gems/1.8/gems/activerecord-1.14.4/lib/active_record/callbacks.rb:254:in
`create_or_update’
/usr/lib/ruby/gems/1.8/gems/activerecord-1.14.4/lib/active_record/base.rb:1392:in
`save_without_validation’
/usr/lib/ruby/gems/1.8/gems/activerecord-1.14.4/lib/active_record/validations.rb:736:in
`save_without_transactions’
/usr/lib/ruby/gems/1.8/gems/activerecord-1.14.4/lib/active_record/transactions.rb:126:in
`save’
/usr/lib/ruby/gems/1.8/gems/activerecord-1.14.4/lib/active_record/connection_adapters/abstract/database_statements.rb:51:in
`transaction’
/usr/lib/ruby/gems/1.8/gems/activerecord-1.14.4/lib/active_record/transactions.rb:91:in
`transaction’
/usr/lib/ruby/gems/1.8/gems/activerecord-1.14.4/lib/active_record/transactions.rb:118:in
`transaction’
/usr/lib/ruby/gems/1.8/gems/activerecord-1.14.4/lib/active_record/transactions.rb:126:in
`save’
/usr/lib/ruby/gems/1.8/gems/activerecord-1.14.4/lib/active_record/associations/association_proxy.rb:110:in
`send’
/usr/lib/ruby/gems/1.8/gems/activerecord-1.14.4/lib/active_record/associations/association_proxy.rb:110:in
`method_missing’
/home/jgarvin/workspace/test_case/config/…/app/models/widget.rb:5:in
save' ./test/unit/widget_test.rb:10:in
test_update’