在Rails(factory_girl)中清除单元和功能测试之间的测试数据库

时间:2009-07-27 16:43:06

标签: ruby-on-rails ruby unit-testing factory-bot

最近我从fixtures切换到factory_girl来测试我的Ruby on Rails应用程序。如果我运行rake test:units,要在my / units目录中运行测试,它们都运行完美。如果我使用rake test:functionals运行我的功能测试(在我的/ functional目录中)也是如此。

但是,如果我只是运行rake测试,同时运行我的单元和功能测试,我的验证在第二组测试(功能,在这种情况下)失败,并显示消息“验证失败:名称已经过取。“

我认为这是由功能测试引起的,这些测试创建的对象具有与单元测试中创建的对象相同的参数 - 这使我相信在单元和功能测试之间不会清除测试数据库。

我使用factory_girl的序列来为对象提供唯一的属性,这意味着factory_girl正在测试之间重置,而数据库却没有。我该怎么做才能解决这个问题?有没有办法在我的两个测试包之间清除数据库?

6 个答案:

答案 0 :(得分:13)

清除(重建)测试数据库的命令行解决方案:

rake db:test:prepare

答案 1 :(得分:12)

尝试在test/test_helper.rb

中写下此内容
eval IO.read(File.expand_path(File.dirname(__FILE__) + "/../Rakefile"))
class Test::Unit::TestCase
 ....
 #db:test:prepare won't work, don't know why,
 #as DROP DATABASE won't execute (me on PostgreSQL).
 #even if I write,
 #ActiveRecord::Base.connection.disconnect!
 Rake::Task["db:reset"].invoke
end

推荐的解决方案。使测试更慢,但有效。

答案 2 :(得分:4)

一个名为“override_rake_task”的rails插件可用于覆盖Rake任务“test”,如果Rails为gem,则在其中定义。这是一项非常简单的任务,一个接一个地执行其他3个任务:测试:单位测试:功能测试:集成。您可以在执行test:functionals之前包括执行“db:test:purge”任务来清除测试数据库。

显然,如果您没有使用此插件,并且如果您在rails应用程序中使用相同的名称定义任务,则rake将执行两个任务:默认和您的。

答案 3 :(得分:2)

以上解决方案对我不起作用。如果您尝试联系外部数据库运行单元测试可能会给出一些奇怪的错误。由于某些原因,在运行测试后它们不会被清除,因此您必须在运行单元测试后运行rake db:test:purge。把它放在Rakefile中,它应该修复它。

Rake::Task["db:test:prepare"].enhance do
  Rake::Task["db:test:purge"].invoke
end

答案 4 :(得分:1)

我在我的机器上遇到了这个问题。我从验证问题中得到测试失败,因为数据库没有在测试之间正确重置。关于我的情况的一些背景故事:

-I had a linux box, and was running code, that I knew should pass the tests.
-I bought a Mac with Lion installed and attempted to get my code running on that machine.
-I installed mysql from source

一切安装得很好。我的数据库工作,rails可以访问它。然而,当我运行测试时,我遇到了同样的问题。我发现了这篇文章,并尝试了两种建议的解决方案(即使它看起来不像代码问题,它似乎是一个配置问题,因为rake在我的linux机箱上运行正常)。这些解决方案都不起作用。

我删除了mysql:

sudo rm /usr/local/mysql
sudo rm -rf /usr/local/mysql*
sudo rm -rf /Library/StartupItems/MySQLCOM
sudo rm -rf /Library/PreferencePanes/My*
sudo rm -rf /Library/Receipts/mysql*
sudo rm -rf /Library/Receipts/MySQL*
sudo rm /etc/my.cnf
sudo rm /usr/local/bin/mysql*

我使用自制软件重新安装了mysql,而不是从源代码手动执行(此步骤是出于同事的建议):

export PATH="/usr/local/bin:/usr/local/sbin:/usr/local/mysql/bin:$PATH"
brew install https://github.com/adamv/homebrew-alt/raw/master/versions/mysql51.rb
unset TMPDIR
mysql_install_db

然后我重新跑了耙子,所有的测试都通过了。如果有人在Lion上,从源代码构建了mysql,并遇到了这个问题,这可能是一个解决方案。

答案 5 :(得分:0)

DB清洁剂是一种非常好的宝石,专门用于测试之间的清洁。它提供了一些选项,包括在事务中包装每个测试并回滚,截断表和删除。

如果您没有使用/使用超过活动记录,它还支持多个ORMS。

文档非常好,包括将其与MiniTest,Rspec和Cucumber一起使用的示例。

https://github.com/bmabey/database_cleaner