Reputation: 4213
I have the following associations:
class Question < ActiveRecord::Base
has_and_belongs_to_many :footnotes
has_and_belongs_to_many :pictures
has_many :fields, :dependent => :destroy
has_many :surveys, :dependent => :delete_all
belongs_to :input
belongs_to :element
has_many :screenshots
belongs_to :standard, :touch => true
belongs_to :product, :touch => true
belongs_to :condition, :class_name => "Field", :touch => true
end
class Product < ActiveRecord::Base
has_many :questions, :dependent => :destroy
has_many :reviews
has_and_belongs_to_many :orders
has_many :competitors
has_many :elements, :dependent => :destroy
has_many :fields
end
class Element < ActiveRecord::Base
has_many :questions
has_many :standards
belongs_to :product, :touch => true
end
class Standard < ActiveRecord::Base
has_many :questions
has_many :standards
belongs_to :review
end
class Footnote < ActiveRecord::Base
belongs_to :reference, :touch => true
has_and_belongs_to_many :questions
end
Why, then, do I get the following?
From: /Users/steven/Dropbox/Testivate/app/controllers/questions_controller.rb @ line 80 QuestionsController#update:
79: def update
=> 80: binding.pry_remote
81: @question = Question.find(params[:id])
82: @question.update_attributes(params[:question])
83: @question.update_columns :product_id => @question.element.product.id
84: flash[:notice] = "Question was successfully updated. (#{undo_link(@question)}.)" if @question.save
85: respond_with @question
86: end
[1] pry(#<QuestionsController>)> @question = Question.find(params[:id])
+----+-----+-----+-----+-----+-----+------+-----+-----+-----+-----+-----+-----+-----+-----+-----+-----+-----+-----+
| id | sta | des | ele | con | cre | upda | add | ins | act | ite | pro | inp | man | abo | res | lev | com | met |
+----+-----+-----+-----+-----+-----+------+-----+-----+-----+-----+-----+-----+-----+-----+-----+-----+-----+-----+
| 1 | 1 | Is | 1 | | 201 | 2014 | tru | On | fal | 1 | 1 | | fal | | | 0 | fal | fal |
+----+-----+-----+-----+-----+-----+------+-----+-----+-----+-----+-----+-----+-----+-----+-----+-----+-----+-----+
1 row in set
[2] pry(#<QuestionsController>)> params
=> {"utf8"=>"✓",
"_method"=>"patch",
"question"=>
{"description"=>"Is it readable?",
"element_id"=>"1",
"standard_id"=>"1",
"about"=>"",
"additive"=>"true",
"iterations"=>"1",
"instructions"=>"On the homepage, there is:",
"picture_ids"=>[""],
"footnote_ids"=>[""],
"active"=>"0",
"manual"=>"0"},
"commit"=>"Update Question",
"action"=>"update",
"controller"=>"questions",
"id"=>"1"}
[3] pry(#<QuestionsController>)> @question.save
=> true
[4] pry(#<QuestionsController>)> @question.update_attributes(params[:question])
NoMethodError: undefined method `#<ActiveRecord::Associations::CollectionProxy::ActiveRecord_Associations_CollectionProxy_Survey:0x0000010b21ce90>' for #<Question:0x0000010c0dda38>
from /Users/steven/.rvm/gems/ruby-2.1.0/gems/activemodel-4.0.2/lib/active_model/attribute_methods.rb:439:in `method_missing'
Upvotes: 8
Views: 19466
Reputation: 76784
Variable
As a general rule, you'd receive a undefined method
error by trying to call a method on an object which either doesn't exist, or is incorrectly defined:
@question.update_attributes(params[:question])
Looks like something to do with this is causing the error
Error
We've had problems like this before, and it's down to this:
ActiveRecord::Associations::CollectionProxy::ActiveRecord_Associations_CollectionProxy_Survey”
As per the Rails documentation:
Association proxies in Active Record are middlemen between the object that holds the association, known as the @owner, and the actual associated object, known as the @target. The kind of association any proxy is about is available in @reflection. That's an instance of the class ActiveRecord::Reflection::AssociationReflection.
What this means is whatever is happening is calling the proxy
object (which basically associates the real objects) in to your methods. Basically you're trying to call methods on an array (collection), rather than the object itself
You'd need to do something like this to fix it:
@question.surveys.first
Fix
I've not used pry
before, but I'd try this:
@question.update(question_params)
private
def question_params
params.require(:question).permit(:description, :element_id, :standard_id, :about, :additive, :iterations, picture_ids: [], footnote_ids: [], :active, :manual)
end
Upvotes: 3