3

私はActiveRecordにまったく慣れていないので、これはおそらくばかげた質問です:私は次のようにメソッドを作成しました:

sample_organizations = [ '37 Signals', 'Fog Creek'] 
sample_organizations.each { |item|
    Organization.first_or_create(
        name: item,
        time_zone: 'Central'
    )
  }

それは機能しませんでした。組織の配列を反復処理してすべてをDBに挿入することを期待していましたが、最初の1行を挿入しただけです。

それから誰かがこのように変更することを提案し、これはうまくいきましたが、誰かが最初の方法で何が間違っていたのかを説明して、私が何をしていたのか/間違っていると仮定したのかを知ることができるかどうか疑問に思いました。

だからこれはうまくいった:

   sample_organizations = [ '37 Signals', 'Fog Creek'] 
    sample_organizations.each { |item|
    Organization.where(name: item).where(time_zone: 'Central').first_or_create
      }
4

2 に答える 2

5

実際には、2つの方法がありますfind_or_create_by。1つの列を追加し、一連の属性を指定します。

したがって、たとえば、次のように書くことができます。

find_or_create_by_name('Willy', time_zone: 'UTC')

2番目はfirst_or_createです。これは提案されたとおりに機能します(2番目の解決策)(ドキュメントも参照してください)。

find_or_createハッシュを受け入れるメソッドを導入する提案がありましたが、その結果、 first_or_create。(ここでの議論を参照してください)。

両方とも、関連するRailsガイドでも詳しく説明されていることに注意してください。

[UPDATE 2014-06-30]現在、表記が変更されていることに注意してください。

Organization.find_or_create_by(name: '37 signals') do |organisation|
  organisation.time_zone = 'Central'
end

名前で組織を検索しようとします。見つからない場合は、ブロックを使用して組織を作成します。注:ブロックは、組織が存在しない場合にのみ実行されます。

于 2013-02-17T17:58:13.333 に答える
4

以下のようになります。

sample_organizations.each { |item|
  Organization.find_or_create_by_name(item, time_zone: 'Central')
}
于 2013-02-17T16:56:03.940 に答える