1


0

Rails HABTM fields_for –同じ名前のレコードが既に存在するかどうかを確認します

モデル「スニペット」と「タグ」の間にはHABTM関係があります。 現在、いくつかのタグを含むスニペットを保存すると、すべてのタグが新しいレコードとして保存されます。

今、同じ名前のタグが既に存在するかどうかを確認したいのですが、その場合、新しいレコードは必要ありません。既存のレコードへのsnippets_tagsのエントリのみが必要です。

これどうやってするの?

snippet.rb:

class Snippet < ActiveRecord::Base
  accepts_nested_attributes_for :tags, :allow_destroy => true, :reject_if => lambda { |a| a.values.all?(&:blank?) }
  ...
end

_snippet.html.erb:

<% f.fields_for :tags do |tag_form| %>

    <%= tag_form.text_field :name, :class => 'tag' %>
    <%= tag_form.hidden_field :_destroy %>

<% end %>

1 Answer


0


OK、私はイライラしています…​しばらくして、私に合った解決策を見つけました。 これが最善の方法かどうかはわかりませんが、それを見せたいです。

Ryan Bates Railscast "Auto-Complete Association "のソリューションを変更する必要がありました。このソリューションは、belongs_to-associationを処理してHABTMで動作させます。

私のスニペットフォームにはtag_namesという名前の新しいテキストフィールドがあり、タグのコンマ区切りリストが必要です。

ライアンのように、仮想属性を使用してタグを取得および設定します。 残りは一目瞭然だと思うので、ここにコードを示します。

「_snippet.html.erb」を表示

  <%= f.label :tag_names, "Tags" %>
  <%= f.text_field :tag_names %>

モデル "snippet.rb":

def tag_names
  # Get all related Tags as comma-separated list
  tag_list = []
  tags.each do |tag|
    tag_list << tag.name
  end
  tag_list.join(', ')
end

def tag_names=(names)
  # Delete tag-relations
  self.tags.delete_all

  # Split comma-separated list
  names = names.split(', ')

  # Run through each tag
  names.each do |name|
    tag = Tag.find_by_name(name)

    if tag
      # If the tag already exists, create only join-model
      self.tags << tag
    else
      # New tag, save it and create join-model
      tag = self.tags.new(:name => name)
      if tag.save
        self.tags << tag
      end
    end
  end
end

これは単なる基本的なコードであり、十分にテストされておらず、改善が必要ですが、一見うまく機能しているようで、解決策があります。