Rails - получение сообщения об ошибке от модели, которая не является ошибкой проверки
Итак, у меня есть метод в модели резервирования, называемый add_equip. Этот метод делает некоторую проверку, чтобы убедиться, что добавленная часть оборудования действительна (не противоречит другому резервированию).
Проверки работают. Если добавленная часть оборудования не должна быть добавлена, это не так, и если это так.
Проблема заключается в том, что я не могу понять, как отправить сообщения обратно на контроллер, чтобы они были помещены во флэш-сообщение? Я знаю, что мне здесь что-то не хватает, но я уже несколько часов искал в Интернете и не могу найти никаких ясных объяснений о том, как передавать ошибки в резервную копию контроллера, если только они не являются ошибками проверки.
add_equip в reservations_controller
def add_equip
@reservation = Reservation.find(params[:id])
@addedEquip = Equip.find(params[:equip_id])
respond_to do |format|
if @reservation.add_equip(@addedEquip)
flash[:notice] = "Equipment was added"
format.html { redirect_to(edit_reservation_path(@reservation)) }
else
flash[:notice] = @reservation.errors
format.html { redirect_to(edit_reservation_path(@reservation)) }
end
end
end
add_equip в модели резервирования
def add_equip equip
if self.reserved.find_by_equip_id(equip.id)
self.errors.add_to_base("Equipment Already Added")
return false
elsif !equip.is_available?(self.start, self.end)
self.errors.add_to_base("Equipment Already Reserved")
return false
else
r = Reserved.new
r.reservation = self
r.equip = equip
r.save
end
end
Любая помощь будет принята с благодарностью. Я знаю, что у меня отсутствует что-то основное.
Ответы
Ответ 1
Использование add_to_base
для хранения сообщения об ошибке кажется мне прекрасным, вам просто нужно выяснить, как его получить в представлении.
Как насчет:
flash[:notice] = @reservation.errors.full_messages.to_sentence
Предполагая, что вы собираетесь повторно отображать форму, вы также можете использовать:
<%= f.error_messages %>
Или, возможно:
<%= error_messages_for :reservation %>
Кроме того, вы можете использовать flash [: error], тогда вы можете по-разному покрасить его с помощью класса CSS.
Ответ 2
Я думаю, я могу понять, почему ошибки не передаются пользователю.
Проблема заключается в том, что вы отправляете перенаправление пользователю, когда действие выходит из строя, а не просто выполняет рендеринг, что означает, что вы теряете любые переменные, которые вы настроили для использования в запросе. Вместо того, чтобы добавлять ошибки во флеш, просто отрисуйте страницу редактирования и установите вспышку в обычное сообщение, и все должно быть хорошо.
Например:
def add_equip
@reservation = Reservation.find(params[:id])
@addedEquip = Equip.find(params[:equip_id])
respond_to do |format|
if @reservation.add_equip(@addedEquip)
flash[:notice] = "Equipment was added"
format.html { redirect_to(edit_reservation_path(@reservation)) }
else
flash[:error] = 'Error adding equipment'
format.html { render :action => :edit }
end
end
end
Теперь вы можете продолжать использовать обычные помощники формы для отображения сообщений об ошибках.
Кроме того, просто небольшое предложение для кода модели, попробуйте использовать i18n, когда это возможно (в том числе для флэш-сообщений в контроллере). Хотя это в основном личное предпочтение, он дает логичный дом для всех ваших сообщений и конкретного текста, а alos позволяет создавать общие или стандартные сообщения, которые можно изменить в одном месте, а не дублировать изменения в нескольких моделях и контроллерах.
например.
def add_equip equip
if self.reserved.find_by_equip_id(equip.id)
self.errors.add_to_base(:already_added)
return false
elsif !equip.is_available?(self.start, self.end)
self.errors.add_to_base(:already_reserved)
return false
else
r = Reserved.new
r.reservation = self
r.equip = equip
r.save
end
end