Domanda

Sto usando FactoryGirl e Faker per generare oggetti utente nel mio file seeds.rb, ma per qualche motivo viene creato lo stesso identico utente e rake db:seed è fallito a causa di una convalida di unicità e-mail.

Fabbrica per gli utenti:

#users.rb
require 'faker'

FactoryGirl.define do
  factory :user do
    first_name            Faker::Name.first_name
    last_name             Faker::Name.last_name
    phone                 Faker::PhoneNumber.cell_phone
    email                 Faker::Internet.email
    password              "password"
    password_confirmation "password"
  end
end
.

E il codice nel file seeds.rb:

#seeds.rb
rand(5..11).times { FactoryGirl.create(:user) }
.

Errore:

ActiveRecord::RecordInvalid: Validation failed: Email has already been taken

Se apro la console e usi FactoryGirl.create(:user) ottengo gli stessi risultati ... Lo stesso oggetto viene creato finito e ancora anche se eseguo solo Faker::Internet.email diverse volte ottenere diverse e-mail.

Factorygirl:

[1] pry(main)> FactoryGirl.create(:user)
...
=> #<User id: 3, first_name: "Osvaldo", last_name: "Wunsch", email: "willy@damore.net", phone: "(912)530-4949 x64848", created_at: "2014-07-31 20:57:27", updated_at: "2014-07-31 20:57:27", encrypted_password: "$2a$10$mxWC7yLYR0m/Sw8MO6Lyru.xuTHCdCEuM9Orx3LXGApF...", reset_password_token: nil, reset_password_sent_at: nil, remember_created_at: nil, sign_in_count: 0, current_sign_in_at: nil, last_sign_in_at: nil, current_sign_in_ip: nil, last_sign_in_ip: nil>
[2] pry(main)> FactoryGirl.create(:user)
...
ActiveRecord::RecordInvalid: Validation failed: Email has already been taken
.

Faker da solo:

[3] pry(main)> Faker::Internet.email
=> "hobart_purdy@goodwinmills.org"
[4] pry(main)> Faker::Internet.email
=> "pierce_brekke@gislasonrolfson.net"
.

Cosa mi manca qui?Perché Faker produce gli stessi dati ogni volta quando viene utilizzato tramite FactoryGirl?

È stato utile?

Soluzione

È necessario passare un blocco se si desidera rivalutare i valori per ogni istanza creata.

invece di

email   Faker::Internet.email
.

prova ...

email   { Faker::Internet.email }
.

Altri suggerimenti

L'uso di Faker per ottenere attributi che passano unicità possono essere un anti-pattern.Potrebbe anche essere una cattiva idea avere l'output semi-casuale di Faker in test - cosa succede se a volte i test falliscono e tu sei fuori a una caccia all'oca selvaggia solo perché Faker ha tossito un valore che non ti aspettavi?

Ultimamente Ho usato le sequenze di FactoryGirl per ottenere valori prevedibili, ma unicizzanti.

FactoryGirl.define do
  factory :user do
    sequence(:first_name, 1) { |n| "John#{n}" }
    sequence(:last_name, 1) { |n| "Doe#{n}" }
    sequence(:phone, 1) { |n| (111111111+n).to_s }               
    sequence(:email, 1) { |n| "email#{n}@example.com" }        
    password              "password"
    password_confirmation "password"
  end
end

FactoryGirl.create(:user).email #=> "email1@example.com"
FactoryGirl.create(:user).email #=> "email2@example.com"
.

Preso da Factory Girl Tips @ http://arjanvandergaag.nl/blog/factory_girl_tips.html

Autorizzato sotto: CC-BY-SA insieme a attribuzione
Non affiliato a StackOverflow
scroll top