5

アップデート

フィクスチャの使用に戻りました。IMOP、備品は工場よりもはるかに優れています。使いやすく、書きやすく、理解しやすい(魔法がない)。私の提案:テストライブラリを非常に基本的なものに制限します(DHHを聞きます)...フィクスチャでミニテストを使用します。

元の投稿

私のアプリでは、地区には多くの学校があり、学校には多くの用途があり、ユーザーには多くのアカウントがあり、アカウントには1つの役割があります。テスト用の完全なファクトリを作成するには、ファクトリ間で存続するユーザーと学校を作成する必要があります。最近の試行で「スタックレベルが深すぎます」というエラーが発生します。

私のuser_test.rb

 FactoryGirl.define do

   factory :district do
     name "Seattle"
   end

   factory :school do
     association :primarycontact, factory: :user # expecting this to attach the user_id from factory :user as :primary contact_id in the school model
     association :district, factory: :district # expecting this to attach the :district_id from the :district factory as :district_id in the school model
     name "Test School"
   end

   factory :user do, aliases: [:primarycontact]
     email "adam@example.com"
     name "Who What"
     username "wwhat"
     password "123456"
     password_confirmation { |u| u.password }
     association :school, factory: :school # expecting this to create :school_id in the users model, using the :school factory
   end

   factory :role do
     name "student"
   end

   factory :account do
     association :user, factory: :user
     association :role, factory: :role
   end

 end

FactoryGirl.create(:account)...そのため、上記の工場のユーザーと役割を使用して、地区に関連付けられている学校に関連付けられているユーザーを使用して、アカウントを作成することを期待していることを実行しようとしています。これは私にはうまくいきません。失敗したテストの中で、「スタックレベルが深すぎます」というエラーが発生します。そして、各DatabaseCleaner.cleanの前に、新しいファクトリの前にテストデータベースをクリアしていると思います。

これらのファクトリを呼び出すテストは次のとおりです。

describe "User integration" do

  def log_em_in
    visit login_path
    fill_in('Username', :with => "wwhat")
    fill_in('Password', :with => "123456")
    click_button('Log In')
  end

  it "tests log in" do
    user = FactoryGirl.create(:account)
    log_em_in
    current_path.should == new_user_path
  end

end

current_path.should == new_user_path returns unknown method error 'should'

このコードを改善して、ファクトリを正しくネストし、テストを続行するためにcurrent_userを取得するにはどうすればよいですか?

モデル

school.rb

  belongs_to :district
  belongs_to :primarycontact, :class_name => "User"
  has_many :users, :dependent => :destroy

user.rb

  belongs_to :school
  has_many :accounts, :dependent => :destroy

district.rb

  has_many :schools

account.rb

  belongs_to :role
  belongs_to :user

role.rb

  has_many :accounts
  has_many :users, :through => :accounts
4

1 に答える 1

12

基本的な問題は、学校を作成するときに(ユーザー)を作成し、次にそのユーザーが学校を作成するという事実によって、userファクトリとファクトリの間に循環依存関係があることです。schoolprimarycontact

工場school内での関連付けの定義方法を変更することで、これを回避できます。userただし、その前に、原則として、関連付けの省略表記を使用することをお勧めします。したがって、これを置き換えます。

factory :account do
  association :user, factory: :user
  association :role, factory: :role
end

これとともに:

factory :account do
  user
  role
end

この簡略化を使用すると、次のファクトリは循環依存を生成せずに必要な処理を実行します。

FactoryGirl.define do

  factory :district do
    name "Seattle"
  end

  factory :school do |school|
    district
    primarycontact
    name "Test School"
    after_build do |s|
      s.primarycontact.school = s
    end
  end

  factory :user do
    email "adam@example.com"
    name "Who What"
    username "wwhat"
    password "123456"
    password_confirmation { |u| u.password }
    school
  end

  factory :primarycontact, class: "User" do
    # add any attributes you want the primarycontact user to have here
  end

  factory :role do
    name "student"
  end

  factory :account do
    user
    role
  end

end

primarycontact私が行ったことは、class: "User"オプションを使用してのファクトリを作成することであることに注意してください。ファクトリとは異なりuser、このファクトリはschoolデフォルトでは作成せず、循環依存を回避します。

次に、school工場では、新しい学校を作成するのではなく、コールバックを使用して学校自体を協会にafter_build割り当てます(これが工場で問題を引き起こしていました)。schoolprimarycontact

それが理にかなっていることを願っています。最新バージョンのfactory_girlでは、コールバック構文が変更されていることに注意してください。詳細については、ドキュメントを参照してください。

于 2013-01-01T08:14:46.300 に答える