1

私は初めて has_many スルーを使用しています。こことガイド をよく読んだにもかかわらず、スルー テーブルの属性にアクセスする正しい方法を理解していません。私のテーブルは、別の投稿のこの例と同じです。

    class Product < ActiveRecord::Base
       has_many :collaborators
       has_many :users, :through => :collaborators
    end

    class User < ActiveRecord::Base
       has_many :collaborators
       has_many :products, :through => :collaborators
   end

   class Collaborator < ActiveRecord::Base
      belongs_to :product
      belongs_to :user
   end

共同作業者テーブルに追加の属性、たとえばhours_spentがあると仮定すると、特定のユーザーと製品の共同作業者テーブルからhours_spentを見つける正しい方法は何ですか?

製品を介してユーザーを見つけ、次のように繰り返し処理している場合

    @product.users.each do |user| 

これはうまくいくようです

    user.collaborator[0].hours_spent

私は正しい値を取得しますが、ユーザー/製品のペアごとに 1 つのコラボレーター レコードしか存在しないはずなので、インデックスが私を混乱させ、何か間違ったことをしていると思います。

読んでくれてありがとう!

編集

おそらく、概念を通じて has_many を取得していません。おそらくMySQLの例が役立つでしょう。

私が考えていたのは

    SELECT * FROM collaborators where user_id = 1;

結果としてセット(ゼロ以上)が期待されます。同様に

    SELECT * FROM collaborators where product_id = 1;

私にもセットをくれますが、

    SELECT * FROM collaborators where user_id = 1 and product_id = 1;

最大で1行になります。

私の理解が正しければ、3 つのクエリはすべてセットを返します。したがって、ある種の一意性制約が必要だと思いますが、それは両方の属しているキーで、ある種の複合キーでなければなりません。それは可能ですか?これをよりよくモデル化する構造はありますか?

迅速かつ有益な回答をありがとうございました!

4

3 に答える 3

0

おそらく、has_and_belongs_to_manyを使用する必要があります。コラボレーターが、ユーザーと製品の間のリンクを作成するためだけに使用され、フィールドが増えない場合。

    class Product < ActiveRecord::Base
       has_and_belongs_to_many :users
    end

    class User < ActiveRecord::Base
       has_and_belongs_to_many :products
   end

間の移行は次のようになります。

class CreateUsersProducts < ActiveRecord::Migration
  def change
    create_table "users_products", :id => false do |t|
      t.integer :user_id
      t.integer :product_id
    end
  end
end
于 2013-02-08T01:44:30.027 に答える
0

ペアごとに 1 つのデータベース行がある場合がありますが、1 人のユーザーを考慮すると、そのユーザーは多くの製品に関連付けられる可能性があるため、ユーザーはコラボレーター テーブルに多くの行を持つことができます。同様に、単一の製品を検討する場合、その製品は多くのユーザーに関連付けることができるため、製品はコラボレーター テーブルに多くの行を持つことができます。

user.collaborators[0].hours_spentまた、 を使用する代わりに、 user.collaborators.first.try(:hours_spent)(null を返す可能性がある) を使用します。

1 人のユーザーが 1 つの製品しか所有できず、1 つの製品が 1 人のユーザーしか所有できない場合は、すべての has_many を has_one に切り替えます。

更新: 上記は、コメントを介して明確化された元の質問に対する回答です。詳細についてはコメントを参照し、Peter による他の回答のコメントを参照してください。

于 2013-02-07T18:19:00.567 に答える