获取工厂内的两个关联以共享另一个关联

sau*_*kko 19 ruby-on-rails factory-bot

我有这5个模型:卫报,学生,关系,关系类型和学校.在他们之间,我有这些联想

class Guardian < ActiveRecord::Base
  belongs_to :school
  has_many :relationships, :dependent => :destroy
  has_many :students, :through => :relationships
end

class Student < ActiveRecord::Base
  belongs_to :school
  has_many :relationships, :dependent => :destroy
  has_many :guardians, :through => :relationships
end

class Relationship < ActiveRecord::Base
  belongs_to :student
  belongs_to :guardian
  belongs_to :relationship_type
end

class School < ActiveRecord::Base
  has_many :guardians, :dependent => :destroy
  has_many :students, :dependent => :destroy
end

class RelationshipType < ActiveRecord::Base
  has_many :relationships
end
Run Code Online (Sandbox Code Playgroud)

我想写一个定义关系的FactoryGirl.每个关系都必须有一个监护人和一个学生.这两个人必须属于同一所学校.监护人工厂与学校有联系,学生工厂也是如此.我一直无法让他们在同一所学校建造.我有以下代码:

FactoryGirl.define do

  factory :relationship do
    association :guardian
    association :student, :school => self.guardian.school
    relationship_type RelationshipType.first
  end

end
Run Code Online (Sandbox Code Playgroud)

当我尝试使用此工厂构建关系时,会导致以下错误:

undefined method `school' for #<FactoryGirl::Declaration::Implicit:0x0000010098af98> (NoMethodError)
Run Code Online (Sandbox Code Playgroud)

有没有办法做我想做的事情,让监护人和学生属于同一所学校,而不必诉诸已经创建的监护人和学生到工厂(这不是它的目的)?

Sim*_*mon 9

这个答案是谷歌"工厂女孩共享协会"的第一个结果,santuxus的回答真的帮助了我:)

以下是有关其他人偶然发现的最新版工厂女孩的语法更新:

FactoryGirl.define do
  factory :relationship do
    guardian
    relationship_type RelationshipType.first

    after(:build) do |relationship|
      relationship.student = FactoryGirl.create(:student, school: relationship.guardian.school) unless relationship.student.present?
    end
  end
end
Run Code Online (Sandbox Code Playgroud)

unless条款防止student在被传递到工厂时被替换FactoryGirl.create(:relationship, student: foo).


san*_*xus 8

我认为这应该有效:

FactoryGirl.define do
  factory :relationship do 
    association :guardian
    relationship_type RelationshipType.first
    after_build do |relationship|
      relationship.student = Factory(:student, :school => relationship.guardian.school)
    end
  end
end
Run Code Online (Sandbox Code Playgroud)