我正在構建一個應用程式,其中使用嵌套屬性在問題記錄下存盤不同的選項記錄。有一個表單,用戶可以在其中動態添加和洗掉選項。在我的創建操作中一切正常,但在更新操作中,如果我洗掉現有選項并提交表單,它不會從資料庫中洗掉。
更新問題記錄的時候,有沒有什么辦法可以完全覆寫現有的嵌套引數,替換為我們在更新請求中傳入的引數?
我知道添加_destroy屬性并將其作為引數傳遞將滿足我的要求。由于我是在按下 UI 中的“洗掉”按鈕時從前端狀態中洗掉選項資訊,因此我不會將其與引數一起發送。Rails 中是否還有其他方法可以完全覆寫嵌套屬性并從控制器本身的更新操作中洗掉那些未在更新請求中傳遞的嵌套記錄?
問題.rb
class Question < ApplicationRecord
belongs_to :quiz
has_many :options
validates :body, presence: true
accepts_nested_attributes_for :options
end
選項.rb
class Option < ApplicationRecord
belongs_to :question
validates :body, presence: true
validates :is_correct, inclusion: { in: [ true, false ], message: "must be true or false" }
end
question_controller.rb
class QuestionsController < ApplicationController
...
def update
@question = Question.find_by(id: params[:id])
if @question.update(question_params)
render status: :ok, json: { notice: t("question.successfully_updated") }
else
render status: :unprocessable_entity, json: { error: @question.errors.full_messages.to_sentence }
end
end
...
private
def question_params
params.require(:question).permit(:body, :quiz_id, options_attributes: [:id, :body, :is_correct])
end
相關問題
uj5u.com熱心網友回復:
如果我理解正確,您將通過單擊選項旁邊的按鈕一個一個地洗掉選項。這實際上不是您需要或想要使用嵌套屬性的東西。嵌套屬性僅在您一次創建/編輯多個記錄時才相關。
雖然您可以通過更新父級來銷毀單個嵌套記錄:
patch '/questions/1', params: {
question: { options_attributes: [{ id: 1, _destroy: true }] }
}
它非常笨重,并不是一個好的 RESTful 設計。
相反,您可以設定一個標準destroy操作:
# config/routes.rb
resources :options, only: :destroy
<%= button_to 'Destroy option', option, method: :delete %>
class OptionsController < ApplicationController
# @todo authenticate the user and
# authorize that they should be allowed to destroy the option
# DELETE /options/1
def destroy
@option = Option.find(params[:id])
@option.destroy
respond_to do |format|
format.html { redirect_to @option.question, notice: 'Option destroyed' }
format.json { head :no_content }
end
end
end
這使用了正確的 HTTP 動詞(DELETE 而不是 PATCH)并清楚地傳達了您在做什么。
uj5u.com熱心網友回復:
我可以分享我最近的專案作業,這有點類似于我使用 shrine gem 上傳影像的地方,我可以更新/銷毀與產品模型 product.rb 關聯的影像
.
.
has_many :product_images, dependent: :destroy
accepts_nested_attributes_for :product_images, allow_destroy: true
product_image.rb
.
belongs_to :product
.
_form.html.erb 用于更新
<%= f.hidden_field(:id, value: f.object.id) %>
<%= image_tag f.object.image_url unless f.object.image_url.nil? %>
<%= f.check_box :_destroy %>
在產品控制器中,我已將其列入白名單
product_images_attributes: [:_destroy,:image, :id]
希望這可以幫助您解決您的案例
轉載請註明出處,本文鏈接:https://www.uj5u.com/yidong/358263.html
標籤:红宝石轨道 红宝石 ruby-on-rails-6.1
