2

Учитывая это определение (с помощью Rails 3.2.13 на Ruby, 2.0.0-P195) ...Как выяснить, какой драгоценный камень рубин угнал ассоциации ActiveRecord метод

class Food < ActiveRecord::Base 
    has_many :recipe_foods, foreign_key: :food_id 

.RESET не действует как документально (он должен сбросить флаг @loaded, но вместо этого он повторно запросов к базе данных и возвращать результаты) ...

2.0.0-p195 :037 > f = Food.last 
    Food Load (1.6ms) ... 
=> #<Food ... 

2.0.0-p195 :038 > f.recipe_foods 
    RecipeFood Load (9.4ms) ... 
=> [#<RecipeFood ... 

2.0.0-p195 :039 > f.recipe_foods.reset 
    RecipeFood Load (10.0ms) ... 
=> [#<RecipeFood ... 

Я подозреваю, что некоторые другие драгоценного камня угнал метод, но это то, что я получаю от .method ...

2.0.0-p195 :040 > f.recipe_foods.method(:reset).source_location 
NameError: undefined method `reset' for class `Array' 

Как определить, какая версия .reset фактически выполняется?

UPDATE:

Когда я пытаюсь вызвать несуществующий метод я получаю этот хаос (в случае, который помогает с тайной):

2.0.0-p195 :052 > f.recipe_foods.snafu 
NoMethodError: undefined method `snafu' for #<ActiveRecord::Relation:0x007fdaef6315b0> 

2.0.0-p195 :053 > f.recipe_foods.method(:snafu) 
NameError: undefined method `snafu' for class `Array' 

ответ

0

Я думаю, что сброс фактически метод объекта AssociationProxy, а не массив, поэтому вы получаете неопределенный метод. Rails 4, кажется, умнее об этом:

> c = Company.first 
> c.users.method(:find) 
=> # <Method: ActiveRecord::Associations::CollectionProxy::ActiveRecord_Associations_CollectionProxy_User(ActiveRecord::Associations::CollectionProxy)#find> 
> c.users.method(:find).source_location 
=> ["/Users/me/.rvm/gems/ruby-2.0.0-p195/gems/activerecord-4.0.0/lib/active_record/associations/collection_proxy.rb", 140] 

Я не уверен, лучшее решение здесь, но я хотел бы видеть, если любой из инструментов в pry может быть полезным.

0

Используйте отладчик. ruby-debug работал до Ruby 1.9; byebug работает на Ruby 2.0.

Написать сценарий с отладчика точки останова прямо перед вызовом, который взлома:

f = Food.last 
rf = f.recipe_foods 
byebug # or debug 
rf.reset 

Затем выполнить сценарий. Отладчик будет разорваться прямо перед вызовом, после чего вы сможете войти, чтобы узнать, какой код действительно выполняется.