RSpec + DatabaseCleaner帮助-拆机过早发生

问题描述

|| 我对RSpec一直迷恋于基于xUnit的测试框架感到有些迷惑,但是我给了它一个机会。 规范编写方式的嵌套性质使我对应该在何处进行数据库设置/拆解感到头痛。 根据DatabaseCleaner自述文件
Spec::Runner.configure do |config|

  config.before(:suite) do
    DatabaseCleaner.strategy = :transaction
    DatabaseCleaner.clean_with(:truncation)
  end

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

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

end
现在我不能使用事务了,因为我在代码中使用了事务,所以我只是坚持截断,但这不应该在这里或那里。 我有这个:
RSpec.configure do |config|
  config.mock_with :rspec

  config.before(:suite) do
    DatabaseCleaner.strategy = :truncation
  end

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

  config.after(:each) do
    DatabaseCleaner.clean
  end
end
这里的问题是,当我尝试在随后的
describe
it
块中使用它们时,我在
subject
let
块中创建的所有灯具都已经从数据库中消失了。 例如(使用机械师创建固定装置...但是不应该如此):
describe User do
  describe \"finding with login credentials\" do
    let(:user) { User.make(:username => \"test\",:password => \"password\") }
    subject { User.get_by_login_credentials!(\"test\",\"password\") }
    it { should == user }
  end
end
我正在为应该如何嵌套这些
describe
subject
以及其他块而苦苦挣扎,所以也许这是我的问题,但是基本上这失败了,因为当它尝试从数据库获取用户时,\由于已调用
after(:each)
钩子而已将其删除,大概是在
let
之后?     

解决方法

如果要一起使用
subject
let
,则需要了解如何/何时调用它们。在这种情况下,在由“ 3”生成的“ 14”方法之前调用“ 2”。问题不在于在调用“ 2”之前已从数据库中删除了该对象,而是在那个时候甚至没有创建该对象。 如果您使用
let!
方法,那么您的示例将起作用,该方法将添加一个
before
钩子,该钩子在示例之前(因此在调用
subject
之前)隐式调用
user
方法。 就是说,我建议您停止努力,并使用RSpec已经公开的更简单的API:
describe User do
  it \"finds a user with login credentials\" do
    user = User.make(:username => \"test\",:password => \"password\")
    User.get_by_login_credentials!(\"test\",\"password\").should eq(user)
  end
end
在我看来,这要简单得多。     ,你写了:   这里的问题是,当我尝试在以下描述或阻止中使用它们时,我在主题或let块中创建的所有固定装置都已经从数据库中消失了。 没错,就是这样。 (并且您不是使用通常的Rails含义的夹具,而是工厂-同样,因为Rails夹具很烂。) 每个单独的规范(即每个
it
块)都从原始数据库开始(或应该开始)。否则,您的测试会泄漏状态并失去原子性。因此,您应该在所需的规范内创建所需的每条记录(或者,如David所说,在18英镑的代码块中减少重复)。 至于组织您的规格...请尽一切可能做。通常,整个班级都会有一个外部
describe
块,对于一组需要共同设置的相关行为或规范,内部会带有
describe
块。每个
describe
上下文可以有自己的
before
after
块。它们像您期望的那样嵌套,因此执行的顺序类似于 外层
before
内部
before
规格 内部
after
外层
after
如果您想查看包含大量RSpec规范和Cucumber故事的项目(尽管每个版本都有较旧的版本),请访问http://github.com/marnen/quorum2。