I am creating a Single Table Inheritance model to build a comment thread and I am getting a confusing routing error
I have set up my Model
class Question < ApplicationRecord
has_many :answers, class_name: 'Questions::Answer'
end
class Answer < ApplicationRecord
has_many :answers, class_name: 'Answers::Answer'
end
with associated sub classes
module Questions
class Answer < ::Answer
belongs_to :question
validates :body, presence: true
validates :question, presence: true
end
end
module Answers
class Answer < ::Answer
belongs_to :answer
has_one :question, through: :answer
validates :body, presence: true
validates :answer, presence: true
end
end
Routes
resources :questions do
resources :answers, shallow: true
end
In my view, I render answers and a form to add an answer
<%= render @answers %></br>
<%= render "answers/form" %>
Which takes the following instances from my Question controller
def show
@answer = @question.answers.new
@answers = @question.answers.page(params[:page]).per(5)
end
However, this gives me an undefined method error:
undefined method `questions_answers_path'
In my routes, indeed the only paths are
question_answers GET /questions/:question_id/answers(.:format) answers#index
POST /questions/:question_id/answers(.:format) answers#create
new_question_answer GET /questions/:question_id/answers/new(.:format) answers#new
edit_answer GET /answers/:id/edit(.:format) answers#edit
answer GET /answers/:id(.:format) answers#show
PATCH /answers/:id(.:format) answers#update
PUT /answers/:id(.:format) answers#update
DELETE /answers/:id(.:format) answers#destroy
The question then is, why is it looking for the plural questions_answers_path
, rather than question_answers_path
.
The form is relatively standard:
<%= simple_form_for(@answer) do |f| %>
<%= f.error_notification %>
<%= f.error_notification message: f.object.errors[:base].to_sentence if f.object.errors[:base].present? %>
<div class="form-inputs">
<%= f.input :body %>
</div>
<div class="form-actions">
<%= f.button :submit %>
</div>
<% end %>
When I force the path by using <%= simple_form_for @answer, url: question_answers_path(@question) do |f| %>
I get an error trying to submit the form. Body can't be blank
Any ideas on what is wrong with my code?
For completeness: Answers Controller
class AnswersController < ApplicationController
before_action :set_answer, only: [:edit, :update, :destroy]
before_action :set_question
def create
@answer = @question.answers.build(answer_params)
respond_to do |format|
if @answer.save
format.html { redirect_to question_path(@question) }
format.json { render :show, status: :created, location: @answer }
else
format.html { render :new }
format.json { render json: @answer.errors, status: :unprocessable_entity }
end
end
end
def update
authorize @answer
respond_to do |format|
if @answer.update(answer_params)
format.html { redirect_to question_answers_path(@question), notice: 'Answer was successfully updated.' }
format.json { render :show, status: :ok, location: @answer }
else
format.html { render :edit }
format.json { render json: @answer.errors, status: :unprocessable_entity }
end
end
end
def destroy
authorize @answer
@answer = Answers.find(params[:id])
@answer.discard
respond_to do |format|
format.html { redirect_to question_answers_path(@question), notice: 'Answer was successfully destroyed.' }
format.json { head :no_content }
end
end
private
def set_answer
@answer = Answer.find(params[:id])
end
def answer_params
params.fetch(:answer, {}).permit(:body, :type).merge(user_id: current_user.id, question_id: @question.id)
end
def set_question
@question = Question.find(params[:question_id])
end
end