11

我是 FactoryGirl 的新手,我正在尝试以下简单的场景?

factory :female, :class => Gender do
  code 'Female'
end

factory :male, :class => Gender do
  code 'Male'
end

factory :papas, :class => Customer do
  first_name 'Jim'
  last_name 'Papas'
  association :gender, :factory => :male, :strategy => :build
end

factory :dumas, :class => Customer do
  first_name 'Mary'
  last_name 'Dumas'
  association :gender, :factory => :female, :strategy => :build
end

然后在我的测试中:

 create(:male)
 create(:female)
 create(:papas)
 create(:dumas)

请注意,Customer 类有一个关联belongs_to Gender类和一个表示gender_id应该存在的验证规则。我还Gender对代码的唯一性进行了类验证。

create(:papas)上面的陈述中,在我的测试中,我得到了Customer将要创建的错误是无效的,因为gender_idnil.

如果我删除与性别的:strategy => :build工厂Customer :papas关联,那么我会收到一个错误,即在尝试创建时:papas,性别的代码已经存在。

我需要做什么才能让我的测试按照上面的要求创建数据?

请注意,在其他测试中,我也希望在没有客户的情况下创建性别。不要告诉我用工厂创建命令创建客户,同时让客户创建性别。如果我也尝试创建两个相同性别的客户,这将不起作用。

此外,必须有一个比这个更好的答案:

@male = create(:male)
@female = create(:female)
create(:papas, :gender => @male)
create(:dumas, :gender => @female)

(使用固定装置时,这些东西是开箱即用的。我应该回到固定装置吗?)

4

3 回答 3

14

您可以通过不为您的性别实例使用工厂和在您的客户工厂中使用回调来实现您想要的。

你并没有从 Gender 工厂中获得很多东西(尽管我很欣赏它可能会为了提出这个问题而简化)。你可以很容易地做到这一点来获得一个性别:

Gender.find_or_create_by_code!('Male')

然后在您的客户工厂中,您可以使用 before 回调来设置性别:

factory :dumas, :class => Customer do
  first_name 'Mary'
  last_name 'Dumas'
  before_create do |customer|
    customer.gender = Gender.find_or_create_by_code!('Female')
  end
end

在 factory_girl 中使用回调的格式最近发生了变化,因此如果您使用的是 3.3 或更高版本,您需要执行以下操作:

before(:create) do |customer|

而不是before_create.

如果创建性别比您的示例更复杂,您仍然可以使用工厂创建性别,但使用回调将它们与您的客户联系起来,而find_by_code!不是使用find_or_create_by_code!.

于 2012-06-01T08:44:29.440 回答
6

ignore已被弃用,并将在 Factory Girl 的第 5 版中删除。

相反,您可以使用瞬态属性

factory :dumas, :class => Customer do
  transient do
    female { Gender.find_by_code('Female') || create(:female) }
  end

  first_name 'Mary'
  last_name 'Dumas'
  gender { female }
end
于 2015-10-20T08:16:15.017 回答
5

ignore块也可用于包装它:

factory :dumas, :class => Customer do
  ignore do
    female { Gender.find_by_code('Female') || create(:female) }
  end

  first_name 'Mary'
  last_name 'Dumas'
  gender { female }
end
于 2013-06-25T14:36:05.437 回答