我有一些带有一些表的rails应用程序(Answer,Question,Project)通过外键将Answer链接到Question,我的QUESTION控制器中的destroy方法定义如下:
def destroy
@pregunta = Question.find(params[:id])
@pregunta.destroy
flash[:danger] = "Se ha borrado la pregunta"
redirect_to questions_path
end
我的答案模型有以下限制:
belongs_to :question, :dependent => :destroy
has_many :answers_projects, :dependent => :destroy
has_many :projects, through: :answers_projects, :dependent => :destroy
但是当我试图像我这样调用我的破坏方法时(在我看来):
<% @preguntas.each do |pregunta| %>
<tr>
<td><%= pregunta.question %></td>
<td><%= pregunta.get_process_name %></td>
<td><%= pregunta.input %></td>
<td><%= pregunta.count_op %></td>
<td><%= pregunta.area %></td>
<td><%= link_to 'Mostrar', question_path(pregunta), class: "btn btn-xs btn-info" %></td>
<td><%= link_to 'Editar', edit_question_path(pregunta) , class: "btn btn-xs btn-warning"%></td>
<td><%= link_to 'DELETE',question_path(pregunta),method: :delete, data: {confirm: '¿Estás seguro de que deseas eliminar la pregunta? Esta acción no se puede deshacer'}, class: "btn btn-xs btn-danger"%></td>
我可以在我的开发环境中销毁记录,但在我的部署环境中,我的Heroku日志中出现以下错误:
AnswersProject Load (0.7ms) SELECT "answers_projects".* FROM "answers_projects" WHERE "answers_projects"."answer_id" = $1 [["answer_id", 95]]
2018-02-02T23:14:19.329550+00:00 app[web.1]: [bb557967-7424-414b-9684-b31ad439936a] (0.6ms) ROLLBACK
2018-02-02T23:14:19.337619+00:00 app[web.1]: [bb557967-7424-414b-9684-b31ad439936a] Completed 500 Internal Server Error in 140ms (ActiveRecord: 30.3ms)
2018-02-02T23:14:19.338990+00:00 app[web.1]: [bb557967-7424-414b-9684-b31ad439936a]
2018-02-02T23:14:19.339160+00:00 app[web.1]: [bb557967-7424-414b-9684-b31ad439936a] NoMethodError (undefined method `each' for #<Answer:0x00000004d173e8>):
2018-02-02T23:14:19.339198+00:00 app[web.1]: [bb557967-7424-414b-9684-b31ad439936a]
2018-02-02T23:14:19.339242+00:00 app[web.1]: [bb557967-7424-414b-9684-b31ad439936a] app/controllers/questions_controller.rb:77:in `destroy'
正如您所看到的,我得到一个NoMethodError(这只在应用程序部署后才会发生)可能是什么原因以及如何解决? 如果需要,我会在我的控制器和模型中发布更多代码,提前感谢:)
修改的 完整的问题控制器:
class QuestionsController < ApplicationController
before_action :require_user
before_action :require_project
before_action :require_user, except: [:new, :create]
before_action :current_project, only: [:index]
def index
@preguntas = Question.all.order(:process)
@project_id = request.original_url.split('.').last
set_current_project(@project_id)
if(@project_id.include? "http")
@project_id = "0"
end
if(@project_id != "0")
@proyecto = Project.find(@project_id)
end
end
def show
@pregunta = Question.find(params[:id])
@opciones = Option.where(question_id: @pregunta)
end
def new
puts "HELLO EVERYONE NEW QUESTION"
@pregunta = Question.new
for option in @pregunta.options
option.question_id = 1
option.build
end
end
def create
puts "HELLO EVERYONE CREATE QUESTION"
@pregunta = Question.new(pregunta_params)
if @pregunta.save
@counter = 0
@step = 1.to_f / @pregunta.options.count
for option in @pregunta.options
@counter = @counter + 1
if @counter == @pregunta.options.count
option.update_value(1.to_f)
else
option.update_value(@step * @counter)
end
end
redirect_to @pregunta
else
render 'new'
end
end
def edit
@pregunta = Question.find(params[:id])
end
def update
puts "HELLO EVERYONE UPDATE UPDATE"
@pregunta = Question.find(params[:id])
@pregunta.options.build
if @pregunta.update(pregunta_params)
@counter = 0
@step = 1.to_f / @pregunta.options.count
for option in @pregunta.options
@counter = @counter + 1
if @counter == @pregunta.options.count
option.update_value(1.to_f)
else
option.update_value(@step * @counter)
end
end
redirect_to @pregunta
else
render 'edit'
end
end
def destroy
@pregunta = Question.find(params[:id])
Answer.where(:question_id => @pregunta.id).destroy_all
@pregunta.destroy
flash[:danger] = "Se ha borrado la pregunta"
redirect_to questions_path
end
def require_same_user
set_project
if current_user != @project.user && !@current_user.admin?
flash[:danger] = "Solo puedes editar tus artículos"
redirect_to root_path
end
end
def require_project
if current_user.projects.count <1 && !current_user.admin?
redirect_to root_path
end
end
private
def pregunta_params
params.require(:question).permit(:question, :value, :process, :area, :input, options_attributes: Option.attribute_names.map(&:to_sym).push(:_destroy))
end
end
修改的 完整问题模型:
class Question < ApplicationRecord
has_many :options, dependent: :destroy
accepts_nested_attributes_for :options, allow_destroy: true, reject_if: proc { |att| att['description'].blank? }
validates :question, presence: true
validates :value, presence: true, length: { minimum: 1 }
validates :area, presence: true, length: { minimum: 3 }
def count_op
Option.where("description IS NOT NULL").where(question_id: self.id).count
end
def get_op
Option.where("description IS NOT NULL").where(question_id: self.id)
end
def get_process_name
case self.process
when 1
"1 - Identificación de grupo"
when 2
"2 - Reflexión de desarrollo comunitario"
when 3
"3 - Problemáticas comunitarias - priorización"
when 4
"4 - Plan de trabajo comunitario"
when 5
"5 - Desarrollo de actividades y proyectos"
when 6
"6 - Operación de proyectos y seguimiento a cumplimiento de metas"
when 7
"7 - Seguimiento a proyectos comunitarios"
when 8
"8 - Fortalecimiento - operación de grupo"
when 9
"9 - Capacitación metodológica para vinculación y desarrollo comunitario"
when 10
"10 - Creación de redes y alianzas comunitarias"
when 11
"11 - Realización de planes de desarrollo local"
when 12
"12 - Seguimiento a proyectos"
when 13
"13 - Fortalecimiento operación de grupo"
when 14
"14 - Creación de redes y alianzas institucionales"
else
"Error en la fase"
end
end
end
答案 0 :(得分:1)
我认为在创建模型时,long
为零,因此当它试图销毁.answer_projects
时,它找不到与.projects
相关联的每个模型。尝试更改
.answer_projects
到
has_many :answers_projects, :dependent => :destroy
has_many :projects, through: :answers_projects, :dependent => :destroy
答案 1 :(得分:0)
你为什么回答belongs_to:question,:dependent =&gt; :破坏? 当你破坏答案时,你想破坏一个问题吗? 你对has_many的答案有疑问吗?
这可能是问题所在。
如果没有,我也发现了一些改进。您正在定义许多实例变量(@ project_id,@ counter,@ step等)。您是否需要在视图中访问这些变量?为什么不使用project_id,counter,step?
修改强>
在QuestionsController中发布错误后#destroy:为什么不在问题模型中添加问题has_many:answers dependent destroy?这样,在销毁问题之前,您不需要执行destroy_all。
class Question < ApplicationRecord
has_many :options, dependent: :destroy
has_many :answers, dependent: :destroy
accepts_nested_attributes_for :options, allow_destroy: true, reject_if: proc { |att| att['description'].blank? }
validates :question, presence: true
validates :value, presence: true, length: { minimum: 1 }
validates :area, presence: true, length: { minimum: 3 }
QuestionsController
def destroy
@pregunta = Question.find(params[:id])
@pregunta.destroy
flash[:danger] = "Se ha borrado la pregunta"
redirect_to questions_path
end