4

関連するコードを貼り付けることから始めて、後で何をしようとしているのかを説明します

class User < ActiveRecord::Base
  has_many :compus, :dependent => :destroy
  has_many :companies, :through => :compus
end

class Company < ActiveRecord::Base
  has_many :compus, :dependent => :destroy
  has_many :employees, :through => :compus, :source => :user
  has_one  :owner, :through => :compus, :source => :user, :conditions => { :owner => true }
end

class Compu < ActiveRecord::Base
  belongs_to :company
  belongs_to :user
end

compus テーブルには次の列があります (移行からコピー)

create_table :compus do |t|
  t.references :company
  t.references :user
  t.string     :job_title
  t.boolean    :owner, null: false, default: false

  t.timestamps
end

ご覧のとおり、n 個の会社を作成し、n 個の会社で仕事をすることができるユーザーがいます。会社で仕事をしているからといって、彼が所有者であるとは限りません。

私が取得したいのは次のとおりです。

user.companies #=> ユーザーが作成した会社、または仕事をしている会社 (後で結果をフィルタリングするのが心配です)

company.employees #=> この会社で仕事をしているすべてのユーザー (compus 経由)

company.owner #=> 最初に会社を作成した 1 人のユーザー (または後で譲渡された場合は別のユーザー)

そのため、上記のコードを書く前に、次の仕様を追加しました。

it "has one owner" do
  company = Factory(:company)
  user    = Factory(:user)

  company.should respond_to(:owner)

  user.companies << company

  company.owner.should === user
end

しかし、次のエラーが発生します。

ActiveRecord::HasOneThroughCantAssociateThroughCollection:
       Cannot have a has_one :through association 'Company#owner' where the :through association 'Company#compus' is a collection. Specify a has_one or belongs_to association in the :through option instead.

会社テーブルに列を追加せずにこの問題を解決するにはどうすればよいですか?会社テーブルにowner_idを追加すると簡単になりますが、データベースで重複が発生します。通常、ユーザーが会社を作成した場合、それは彼が働いていることを意味しますそれ

私がそれに取り組んでいる間の別の質問です。関連付けを介して compus テーブルにある :job_title に簡単にアクセスするにはどうすればよいですか?

4

1 に答える 1

8

所有者を返す関数を作成するだけです

def owner
    compus.where(:owner => true).first
end

データベース設計の観点から、企業を 1 人の所有者に限定したい場合は、company テーブルに owner_id 列を配置することをお勧めします。そうしないと、所有者が常に 1 人であることを強制する必要があり、より複雑になります。

于 2011-06-25T17:57:21.620 に答える