Проблема проверки с автотестом и Factory Girl - PullRequest
3 голосов
/ 05 января 2011

У меня проблема с автотестом.В моей модели пользователя уникальны имя пользователя и адрес электронной почты.Когда я запускаю автотест, все работает нормально.Во втором раунде, из автотеста, у меня

Проверка не удалась: электронная почта уже была принята, имя пользователя уже было взято

ошибка только в двух тестах.Я не понимаю, почему, я использую factorygirl с последовательностью, и это должно генерировать каждый раз новое имя пользователя.

Это мой файл rspec2:

describe User do

  specify {  Factory.build(:user).should be_valid }

  context "unique values" do

    before :all do
       @user = Factory.create(:user)
    end


    it "should have an unique email address" do
       Factory.build(:user, :email  => @user.email).should_not be_valid
    end

    it "should have an unique username" do
       Factory.build(:user, :username  => @user.username).should_not be_valid
    end

  end


  context "required attributes" do

    it "should be invalid without an email address" do
       Factory.build(:user, :email => nil).should_not be_valid
    end

    it "should be invalid without an username" do
       Factory.build(:user, :username  => nil).should_not be_valid
    end

    it "should be invalid without an password" do
       Factory.build(:user, :password  => nil).should_not be_valid
    end

    it "should be invalid without an address" do
        Factory.build(:user, :address  => nil).should_not be_valid
    end


  end
end

Фабрика:

Factory.sequence :username do |n|
  "Outfit#{n}er"
end

Factory.sequence :email do |n|
  "user#{n}@example.com"
end

Factory.define :user do |u|
  u.username              { Factory.next :username }
  u.email                 { Factory.next :email }
  u.password              'secret'
  u.phone_number          '02214565854'
  u.association :address, :factory => :address
end

Factory.define :confirmed_user, :parent => :user do |u|
  u.after_build { |user| user.confirm! }
end

Единственные два теста, которые не работают, находятся в контексте «уникальных значений».Все остальные тесты работают без ошибок.

Спасибо

Ответы [ 4 ]

1 голос
/ 26 августа 2011

Это именно та проблема, с которой я только что столкнулся - и у меня был странный опыт, когда эта проблема, похоже, не возникала, если я просто запускал "rake spec".

Не найдя очевидного ответа, я попробовал что-то, что, похоже, решило проблему! Кажется, что установка переменной класса внутри блока before () является виновником, если вы используете FactoryGirl.

У меня было что-то очень похожее:

factory :widget do
  sequence(:name) { |n| "widget#{n}" }
end

, то:

describe Widget do
  before(:each) { @widget = FactoryGirl.create(:widget) }
  it ...yadda yadda...
    @widget.foo()
  end
end

автотест найдет проблемы ограничения уникальности. Я изменил тест rspect на это:

describe Widget do
  let(:widget) { FactoryGirl.create(:widget) }
  it ...yadda yadda...
    widget.foo()
  end
end

... и проблемы ограничения уникальности исчезли. Не уверен, почему это происходит, и похоже, что не должно произойти , но может быть работоспособным разрешением.

1 голос
/ 16 ноября 2011

Я получил эту проблему из-за того, что база данных не очищалась должным образом после некоторых тестов.

Если вы запустите: грабли дб: тест: подготовить до автотеста, это все еще происходит?

В конце концов я справился с этим, изолировав, какие тесты не были очищены, и исправив их (или удалив их). Извините, я не могу вспомнить, в чем была проблема, но произошла ошибка, вызвавшая ее.

О, и я запустил его без spork, так что я мог видеть мои сообщения регистратора, смешанные с результатами.

Надеюсь, это поможет.

0 голосов
/ 20 декабря 2012

У меня возникла очень похожая проблема, и я безуспешно попробовал несколько предложений в этой теме. Однако я исправил это, добавив в свой spec_helper.rb следующее:

# Clean up the database
  require 'database_cleaner'
   config.before(:suite) do
     DatabaseCleaner.strategy = :truncation
     DatabaseCleaner.orm = "mongoid"
  end

  config.before(:each) do
    DatabaseCleaner.clean
  end

Также не забудьте добавить гем DatabaseCleaner в свой гемфайл

0 голосов
/ 05 января 2011

Проблема, вероятно, в вашем конфигурационном файле.У вас есть строка в вашем конфигурационном файле spec (возможно, spec_helper.rb), которая гласит:

config.use_transactional_fixtures = false

Это должно быть:

config.use_transactional_fixtures = true

Или, если вы не хотите использовать транзакциюВ ваших тестах у вас должна быть функция before (: each):

before :each do
  User.destroy_all
end

В качестве альтернативы я использую Gem Sham для своих фабрик, потому что он более совместим с нетранзакционными приборамии последовательности.

...