This is the error:
NoMethodError in VideosController#update
undefined method `each' for #<Topic:0x1032ee开发者_如何学编程330>
This is the application trace:
app/models/video.rb:19:in `assign_topics'
app/controllers/videos_controller.rb:41:in `update'
app/controllers/videos_controller.rb:40:in `update'
this is my assign_topics
method:
def assign_topics
if @topic_names
self.topics = Topic.find_or_create_by_name(@topic_names)
end
end
Note that I'm following this: http://media.railscasts.com/videos/167_more_on_virtual_attributes.mov
Here's the video controller's update method:
def update
@video = current_user.videos.find(params[:id])
respond_to do |format|
if @video.update_attributes(params[:video])
format.html { redirect_to(@video, :notice => 'Video was successfully updated.') }
else
format.html { render :action => "edit" }
end
end
end
I'd guess that your assign_topics
method is at fault. Topic.find_or_create_by_name
will return a single Topic
instance, then you assign that to self.topics
and self.topics
is probably expecting an Array
(or some other Enumerble
); then later, the update process will try to loop through self.topics
using each
and you get your error.
You mention, in a comment, that you tried something like this:
self.topics = @topic_names.each { |n| Topic.find_or_create_by_name(n) }
But that won't work because each
returns the original array and so the above is equivalent to this:
@topic_names.each { |n| Topic.find_or_create_by_name(n) }
self.topics = @topic_names
and all the Topic
instances that you found/created are simply thrown away.
So, you might have better luck using collect
like this:
def assign_topics
if @topic_names
self.topics = @topic_names.collect { |n| Topic.find_or_create_by_name(n) }
end
end
You are getting a NoMethodError Exception
because somewhere in your code you are trying to loop, via .each()
, on something that is not an array/enumerable.
According to your exception, you are calling .each()
on a Model Object(Topic), which would make sense to not have the .each()
method.
精彩评论