Ruby on rails 与同一父母有多个关联的工厂女孩

Ruby on rails 与同一父母有多个关联的工厂女孩,ruby-on-rails,activerecord,factory-bot,Ruby On Rails,Activerecord,Factory Bot,如何创建具有多个依赖于同一父级的关联的工厂 父模型: class Parent < ActiveRecord::Base has_many :codes has_many :parent_filters validates :parent, :presence => true, :uniqueness => true end 因此,分配给AdhocMapping的代码和ParentFilter具有相同的父级。我尝试了许多不同的方法,试图让它在FactoryGir

如何创建具有多个依赖于同一父级的关联的工厂

父模型:

class Parent < ActiveRecord::Base
  has_many :codes
  has_many :parent_filters

  validates :parent, :presence => true, :uniqueness => true
end
因此,分配给AdhocMapping的代码和ParentFilter具有相同的父级。我尝试了许多不同的方法,试图让它在FactoryGirl中工作,但我似乎无法让它创建对象

这是我认为最接近我想要的工厂:

require 'faker'

FactoryGirl.define do
  factory :adhoc_mapping do |f|
    transient do
     p Parent.where(:parent => Faker::Lorem.word).first_or_create
    end

    association :parent_filter, :parent => p
    association :code, :parent => p
    association :adhoc_attribute
  end
end

它给出了一个
Trait not registed:p
错误,对于我通常在
FactoryGirl
中(:build)之后使用的
关联,然后我可以准确地判断应该发生什么。(
association xxx
经常不能像我希望的那样工作,真让我感到羞耻。)

因此,在您的情况下,我认为您可以通过以下方法解决此问题:

require 'faker'

FactoryGirl.define do
  factory :adhoc_mapping do |f|
    transient do
      default_parent { Parent.where(parent: Faker::Lorem.word).first_or_create }

      parent_filter {  FactoryGirl.build(:parent_filter, parent: default_parent) }
      code { FactoryGild.build(:code, parent: default_parent) }
      adhoc_attribute { FactoryGirl.build(:adhoc_attribute) }
    end

    after(:build) do |adhoc_mapping, evaluator|
      adhoc_mapping.parent_filter = evaluator.parent_filter
      adhoc_mapping.code = evaluator.code
      adhoc_mapping.adhoc_attribute = evaluator.adhoc_attribute
    end
  end
end

通过在(:build)
之后使用
,它可以与
FactoryGirl.create
FactoryGirl.build
一起使用。除了
transient default\u parent
,您甚至可以在构建
adhoc\u映射时显式设置想要的父级。现在,在编辑之后您还可以将
nil
传递给属性,它将不会被覆盖。

只需快速注释
p(…)
就可以打印到屏幕上,也许这就是为什么您会出现此错误?尝试另一个变量,可能FG的作用域规则有点混乱。如果将其更改为
pnt
,则不会有任何更改。我认为您无法以这种方式访问瞬态属性,我添加了一个答案,说明如何在(:build)
之后使用
。这似乎可行。我想我们快到了。现在,它在两个路径中创建了一个具有相同父对象的有效对象,但当我将“:Parent_filter'、“:code”或“:adhoc_attribute”设置为nil并检查是否存在无效状态时,它仍然显示为有效。当我添加一个规则来检查它们是否被设置为nil时,它会失败,并说它们有一个该类型的对象,因此nil设置无法通过。这适用于所有测试用例。非常感谢您提供此解决方案。
class AdhocAttribute < ActiveRecord::Base
  has_many :adhoc_mappings

  has_many :codes, :through => :adhoc_mappings
  has_many :parent_filters, :through => adhoc_mappings

  validates :adhoc_attribute, :presence => true, :uniqueness => true
end
class Code < ActiveRecord::Base
  belongs_to :parent

  has_many :adhoc_mappings
  has_many :adhoc_attributes, :through => :adhoc_mappings

  validates :code, :parent, presence: true
  validates :code, uniqueness: {case_sensitive: false}
end
class AdHocMapping < ActiveRecord::Base

  belongs_to :code
  belongs_to :parent_filter
  belongs_to :adhoc_attribute

  has_one :company, :through => :parent_filter

  validates :code, :parent_filter, presence: true
  validates :code, :uniqueness => { :scope => :parent_filter }
end
p = Parent.where(:parent => "Papa").first_or_create
aa = AdhocAttribute(:adhoc_attribute => "Doodle").first_or_create
f = Filter.where(:filter => "Z..W").first_or_create
c = Code.where(:code => "ZYXW", :parent => p).first_or_create
pf = ParentFilter.where(:parent => p, :filter => f).first_or_create
am = AdhocMapping(:adhoc_attribute => aa, :parent_filter => pf, :code => :c).first_or_create
require 'faker'

FactoryGirl.define do
  factory :adhoc_mapping do |f|
    transient do
     p Parent.where(:parent => Faker::Lorem.word).first_or_create
    end

    association :parent_filter, :parent => p
    association :code, :parent => p
    association :adhoc_attribute
  end
end
require 'faker'

FactoryGirl.define do
  factory :adhoc_mapping do |f|
    transient do
      default_parent { Parent.where(parent: Faker::Lorem.word).first_or_create }

      parent_filter {  FactoryGirl.build(:parent_filter, parent: default_parent) }
      code { FactoryGild.build(:code, parent: default_parent) }
      adhoc_attribute { FactoryGirl.build(:adhoc_attribute) }
    end

    after(:build) do |adhoc_mapping, evaluator|
      adhoc_mapping.parent_filter = evaluator.parent_filter
      adhoc_mapping.code = evaluator.code
      adhoc_mapping.adhoc_attribute = evaluator.adhoc_attribute
    end
  end
end