在我的 Rails 電影資料庫中,我現在添加了一個可以標記電影和演員的“標記”模型。但是,我無法洗掉用于標記電影或演員之一的標簽(foreign_key 約束);當我在這樣的標簽上呼叫 destroy 時,Rails 說:
Mysql2::Error: Cannot delete or update a parent row: a foreign key constraint fails (`newmovie_development`.`taggings`, CONSTRAINT `fk_rails_e21d88485b` FOREIGN KEY (`tag_id`) REFERENCES `tags` (`id`))
電影(演員在這方面完全一樣):
class Movie < ApplicationRecord
...
has_many :taggings, as: :taggable, dependent: :destroy
has_many :tags, through: :taggings
...
標簽:
class Tag < ApplicationRecord
validates :name, presence: true
has_many :taggings
has_many :movies, through: :taggings, :source => 'taggable', :source_type => 'Movie'
has_many :actors, through: :taggings, :source => 'taggable', :source_type => 'Actor'
end
標記:
class Tagging < ApplicationRecord
belongs_to :tag
belongs_to :taggable, polymorphic: true
end
uj5u.com熱心網友回復:
你可能在這里有點困惑。如果您有想要編輯標簽的電影或演員,可以使用tags_ids=由has_many :tags.
<%= form_with(model: @actor) do |form| %>
<div class="field">
<%= form.label :tags_ids, 'Tags' %>
<%= form.collection_checkboxes :tag_ids, Tag.all, :id, :name %>
</div>
<% end %>
class ActorsController < ApplicationController
before_action :set_actor, except: [:new, :create, :index]
def update
if @actor.update(actor_params)
redirect_to @actor, success: 'Actor updated'
else
render :new
end
end
private
def set_actor
@actor = Actor.find(params[:id])
end
def actor_params
params.require(:actor)
.permit(:foo, :bar, tag_ids: [])
end
end
這將自動將引數中傳遞的陣列與標記表中的任何現有行進行比較,并相應地添加/創建行。
如果您想創建一個按鈕以逐個“從可標記中洗掉標簽”(可能使用 ajax 進行了增強),您需要確保您實際上是從標記表中洗掉行而不是標簽:
module Actors
class TagsController < ApplicationController
# DELETE /actors/1/tags/2
def destroy
@tagging = @actor.taggings.find_by!(tag_id: params[:id])
@tagging.destroy
end
private
def set_actor
@actor = Actor.find(params[:actor_id])
end
end
end
如果您確實想從整個系統中完全洗掉標簽(在 Stackoverflow 上等同于燒毀),您需要在關聯上設定依賴選項,以便不違反外鍵約束:
class Tag < ApplicationRecord
validates :name, presence: true
has_many :taggings, dependent: :destroy
# ...
end
您還應該確保添加唯一索引以確保您不會在標記表中得到重復項:
add_index :taggings, [:tag_id, :taggable_id, :taggable_type], unique: true
和驗證:
class Tagging
validates_uniqueness_of :tag_id, scope: [:taggable_id, :taggable_type]
end
轉載請註明出處,本文鏈接:https://www.uj5u.com/caozuo/416954.html
標籤:
下一篇:白話linux作業系統原理
