Faker在factory_girl中使用时会产生重复的数据

我试图使用Faker gem填充一些伪造的数据到工厂:

Factory.define :user do |user| user.first_name Faker::Name::first_name user.last_name Faker::Name::last_name user.sequence(:email) {|n| "user#{n}@blow.com" } end 

但是,当我期望这产生具有不同first_name和last_names的用户时,每个用户都是一样的:

 >> Factory(:user) => #<User id: 16, email: "user7@blow.com", created_at: "2011-03-18 18:29:33", updated_at: "2011-03-18 18:29:33", first_name: "Bailey", last_name: "Durgan"> >> Factory(:user) => #<User id: 17, email: "user8@blow.com", created_at: "2011-03-18 18:29:39", updated_at: "2011-03-18 18:29:39", first_name: "Bailey", last_name: "Durgan"> 

我怎样才能让Faker gem为每个用户生成新的名字,而不是只重用原来的名字?

 Factory.define :user do |user| user.first_name { Faker::Name::first_name } user.last_name { Faker::Name::last_name } user.sequence(:email) {|n| "user#{n}@blow.com" } end 

试着在法克斯周围加上括号。 看到这个链接

请注意,由于可用的假数据有限,Faker可能仍然会提供重复的数据。

为了简单的testing目的,并通过唯一性validation,我使用了以下内容:

 sequence(:first_name) {|n| Faker::Name::first_name + " (#{n})"} sequence(:last_name) {|n| Faker::Name::last_name + " (#{n})"} 

为了保持正确的答案,这里是从博客转移,我没有信用的答案。

如果你使用下面的代码,faker将不会产生独特的名字

 Factory.define :user do |u| u.first_name Faker::Name.first_name u.last_name Faker::Name.last_name end 

然而,把大括号放在faker的周围使它成功!

 Factory.define :user do |u| u.first_name { Faker::Name.first_name } u.last_name { Faker::Name.last_name } end 

为了解释为什么,第一个例子是产生相同的名字。 这只是评估一次。 第二个例子每次使用工厂时都进行评估。

这是由于{}提供了懒惰的评估。 基本上他们提供了一个proc / lambda与Faker调用作为它们的返回值。

在对属性进行唯一性validation时,使用序列的替代方法(效率较低)是检查提议的值是否已经存在,并继续尝试新值直到它是唯一的:

 FactoryGirl.define do factory :company do name do loop do possible_name = Faker::Company.name break possible_name unless Company.exists?(name: possible_name) end end end end