我设置了两个 collections, 分别是 entries 和 entry_aliases。用 has_and_belongs_to_many 关系。entry_alias 只有一个
field :name, type: String validates :name, uniqueness: true`
entry model 里加上accepts_nested_attributes_for :entry_alias
并使用 nested_form 来动态添加 entry_aliases_attributes。
在 entry model 下
_destroy == '1'
的 entry_alias 不被创建。数据表内已有同名的则不创建并关联已有同名 entry_alias. _destroy == '1'
或者 name 更改的 entry_alias 被取消关联。寻找并创建 name 对应的 entry_alias.entry_alias 只能被创建,不能被删除,或者更改 name.
我最后的实现就是下面这么多代码,非常头疼。高手有妙招么?
def save
ids = []
self.entry_aliases.each do |item|
alias_by_name = EntryAlias.find_or_create_by(name: item.name)
alias_by_name.update_attributes(entry_ids: alias_by_name.entry_ids | [self.id])
ids << alias_by_name.id
end
self.entry_aliases = []
self.entry_alias_ids = ids
super
end
def update_attributes(params)
params[:entry_aliases_attributes].each do |key, entry_alias|
if entry_alias[:_destroy] == '1' && entry_alias[:id]
alias_by_id = EntryAlias.find(entry_alias[:id])
if alias_by_id
alias_by_id.update_attributes(entry_ids: alias_by_id.entry_ids - [self.id])
super(entry_alias_ids: self.entry_alias_ids - [alias_by_id.id])
end
elsif entry_alias[:_destroy] != '1' && entry_alias[:id]
alias_by_id = EntryAlias.find(entry_alias[:id])
if alias_by_id && alias_by_id.name != entry_alias[:name]
alias_by_id.update_attributes(entry_ids: alias_by_id.entry_ids - [self.id])
super(entry_alias_ids: self.entry_alias_ids - [alias_by_id.id])
entry_alias.delete(:id)
elsif !alias_by_id
entry_alias.delete(:id)
end
end
end
params[:entry_aliases_attributes].delete_if { |key, value| value[:_destroy] == '1' }
super
end