`
thundercao
  • 浏览: 13751 次
最近访客 更多访客>>
社区版块
存档分类
最新评论

Rails单元测试的一点点疑惑

阅读更多
今天在做单元测试时发现一个小问题,就是如果运行多个测试类,会因为外键问题无法删除测试数据导致测试失败.如下:

测试类一
ruby 代码
 
  1. require File.dirname(__FILE__) + '/../test_helper'  
  2.   
  3. class ShareTest < Test::Unit::TestCase  
  4.   self.use_transactional_fixtures = true  
  5.   fixtures :users,:share_catagories,:shares  
  6.   # Replace this with your real tests.  
  7.   def test_last_shares  
  8.     assert_not_nil Share.last_shares(5)  
  9.   end  
  10.     
  11. end  

测试类二
ruby 代码
 
  1. require File.dirname(__FILE__) + '/../test_helper'  
  2.   
  3. class BlogTest < Test::Unit::TestCase  
  4.   self.use_transactional_fixtures = true  
  5.   fixtures :users,:blogs,:blog_members  
  6.      
  7.   def test_hearty_seniority  
  8.     assert_not_nil Blog.hearty_seniority(2)  
  9.   end  
  10.   
  11. end  

表间关系:
   user 与 blog 是一对一,blog与 blog_members是一对多,share_catagoriesshares也是一对多,user与shares也是一对多
问题症状:
   如果先运行ShareTest,测试通过.再运行BlogTest时夹具在测试方法运行前初始化数据,实际上是删除表再建表的一个过程,但因为前面运行过ShareTest了,此时在对user表初始时就会发生有外键引用(shares),无法初始化(fixtures),导致测试失败.
解决方法:
   将表间的外键关系删除.

这个问题到也不是什么大问题,后来看了一下typo的建表脚本,确实是没有外键,但有点想不明白,难道在设计数据库时不需要用到外键?还是说在测试时将外键删除掉,正式发布时还在用带有外键的脚本建表.typo已经是一个可以放在生产环境下使用的系统了,它就不需要外键,全部通过程序控制?或者说在Model里定义表关联时用dependent参数来保证外键?

我个人也不喜欢使用各种数据库自有的特性,但外键却是大多数数据库支持的东西,如果仅是因为测试而去除这个强大的功能,好像有点........
分享到:
评论
4 楼 thundercao 2007-09-07  
试试看
3 楼 Readonly 2007-09-07  
check out
http://dev.rubyonrails.org/ticket/2404

一个已经存在了2年的争论,rails team的人一直以为了保障unit test速度为理由,不肯打这个patch,简直是OOXX...

这个问题还不单单是外键问题,在一些牵涉到统计的测试用例里面,也会有前一个unit test fixuture没有清理干净,导致断言出错的情况。

偶建议用讨论里面有个rick发的patch,很简洁地解决了这个问题。
2 楼 dogstar 2007-09-07  
外键的作用无外乎是保证数据完备,这些可以用程序做到。而且,使用数据库这些特性的话也有很大的开销,不完备检查呀之类的。就我目前的经验来看,没有必要使用外键。至少我到现在从来没有用过。
1 楼 pig345 2007-09-07  
似乎Rails有意在回避这个问题。
他都没有内置对外键的自动支持。

相关推荐

Global site tag (gtag.js) - Google Analytics