为什么在后钩中添加“sleep 1”会导致此Rspec / Capybara测试通过?
我使用的是rails 4.0.5,rspec 2.14.1,capybara 2.2.1,capybara-webkit 1.1.0和database_cleaner 1.2.0。 我通过以下function测试看到一些奇怪的行为(模拟用户在post上查看评论,将鼠标hover在图标上以显示菜单,然后单击菜单项以删除评论):
let(:user){create(:user)} let(:post){create(:post, author: user)} let!(:comment){create(:comment, post: post, author: user)} ... it "can delete a comment" do assert(page.has_css? "#comment-#{comment.id}") find("#comment-#{comment.id}-controls").trigger(:mouseover) find("#comment-#{comment.id} .comment-delete a").click assert(page.has_no_css? "#comment-#{comment.id}") end
这个测试大约80%的时间都失败了,总是由于某些记录从数据库中检索为nil
– 我得到NoMethodError: undefined method X for nil:NilClass
,对于各种X值。有时nil是正在评论的删除,有时它是评论附加的post,有时它是评论/post的作者。
如果我在测试结束时添加sleep 1
,它会通过:
it "can delete its own comment" do assert(page.has_css? "#comment-#{comment.id}") find("#comment-#{comment.id}-controls").trigger(:mouseover) find("#comment-#{comment.id} .comment-delete a").click assert(page.has_no_css? "#comment-#{comment.id}") sleep 1 end
如果我把sleep 1
放在after
块中,它也会通过。
知道为什么我得到这些NoMethodErrors,和/或为什么测试通过,如果我在完成所有工作后让它睡了一秒钟?
我怀疑在您从数据库中删除注释之前,您的应用程序中的注释可能会从页面中消失(这是您断言的最后一件事)。 这意味着测试可以在删除发生之前进行清理。 如果是这种情况,您可以通过等待在测试结束时发生实际删除来修复它。 我有这种方法(重新实现从Capybara 2中删除但仍有时需要的方法 )
def wait_until(delay = 1) seconds_waited = 0 while ! yield && seconds_waited < Capybara.default_wait_time sleep delay seconds_waited += 1 end raise "Waited for #{Capybara.default_wait_time} seconds but condition did not become true" unless yield end
所以我能做到
wait_until { Comment.count == 0 }
在测试中。
另一种方法是添加Rack中间件,以阻止测试结束后发出的请求。 这里详细描述了这种方法: http : //www.salsify.com/blog/tearing-capybara-ajax-tests我看到它在一个大规模的RSpec特性规范中解决数据泄漏问题做得很好。
https://github.com/jnicklas/capybara#asynchronous-javascript-ajax-and-friends
使用异步JavaScript时,您可能会遇到尝试与页面上尚不存在的元素进行交互的情况。 Capybara通过等待页面上显示的元素自动处理此问题。
- 使用Rspec + Capybara在Rails中测试错误页面
- 为什么即使我删除了application.js文件,Capypara + Rspect测试仍然通过?
- Rails – 如何为存根/伪造的http或ajax响应存根特定的响应时间
- 从capybara-webkit #execute_script访问DOM?
- 使用Capybara Webkit 1.3.1测试警报对话框文本
- 未定义的方法’has_selector?’ 用于rspec装饰器
- 使用Capybara + Rails3找不到要点击的元素
- 为什么capybara在请求规格中不可用?
- 使用Capybara / Selenium Webdriver测试HTML5文件上传 – Ruby