ljnissen
ljnissen

Reputation: 139

Finding specific database entries when using nested attributes in RoR

I'm using nested attributes in my Ruby on Rails app (4.0.2) such that survey has_many questions and accepts_nested_attributes_for questions and question belongs_to survey.

The problem that I have run into is that when I only want to look at the questions that belong to a particular survey I get an "undefined method "id" for nil:NilClass"-error. When on the other hand I look at all the questions the index action works without problems.

My questions controller index action:

  def index
     @questions = Question.where(:survey_id => @survey.id).all # if instead I use @questions = Question.all it works fine, but is not what I want.
     #@questions = @survey.questions.all
     @surveys = Survey.all
     @survey = Survey.first
 end

My surveys/index.html.erb page:

  <%= link_to("questions", { :controller => 'questions', :survey_id => survey.id }, :class => 'btn btn-xs') do %>
        <%= glyph 'th-list' %>
  <%- end -%>

My Question model:

 class Question < ActiveRecord::Base
   belongs_to :survey
   scope :sorted, lambda { order("questions.created_at ASC")}
 end

I also use a before_action that I call find_survey which looks like this:

def find_survey
  # If in each action calling this method (find_survey) has :survey_id sent
  if params[:survey_id]
    # We will then go to the database and look for (and find) :survey_id and set that to @survey. 
    @survey = Survey.find(params[:survey_id])
  end
end

Could anybody point me in the right direction?

Upvotes: 0

Views: 51

Answers (2)

george
george

Reputation: 163

The undefined method on NilClass is because your instance variable @survey is nil, and when you're calling Question.where(:survey_id => @survey.id).all you're getting that error.

If you're associations are set up right you should be able to run @survey.questions and not have to perform the search on Questions. That's part of ActiveRecord rails magic. You SHOULDN'T have to call @survey.questions.all because that will return all intances of the Question class, leave that off and you should be good to go.

As far as why this isn't working for you now, it may just be an order thing — you're calling @survey before you define it on the line below.

Upvotes: 1

stoodfarback
stoodfarback

Reputation: 1349

Based on the error you posted, @survey is likely nil in this line:

@questions = Question.where(:survey_id => @survey.id).all

So maybe your "before_action" is not being called?

Upvotes: 0

Related Questions