我已实施a solution similar to this来修剪我的数据库。
# model.rb
after_create do
self.class.prune(ENV['VARIABLE_NAME'])
end
def self.prune(max)
order('created_at DESC').last.destroy! until count <= max
end
这在手动测试中效果很好。
在RSpec中,测试如下:
# spec/models/model_spec.rb
before(:each) do
@model = Model.new
end
describe "prune" do
it "should prune the database when it becomes larger than the allowed size" do
25.times { create(:model) }
first_model = model.first
expect{create(:model)}.to change{Model.count}.by(0)
expect{Model.find(first_model.id)}.to raise_error(ActiveRecord::RecordNotFound)
end
end
end
结果是
1) Model prune should prune the database when it becomes larger than the allowed size
Failure/Error: expect{Model.find(first_model.id)}.to raise_error(ActiveRecord::RecordNotFound)
expected ActiveRecord::RecordNotFound but nothing was raised
在测试执行期间检查数据库显示对order('created_at DESC').last
的调用正在产生在25.times
块(模型#2)中创建的模型的第一个实例,而不是在before(:each)
块中创建的模型{1}}块(模型#1)。
如果我改变了行
25.times { create(:model) }
到
25.times { sleep(1); create(:model) }
测试通过了。如果我改为sleep(0.1)
,则测试仍然失败。
这是否意味着如果我的应用程序在彼此的1秒内创建两个或更多个Model实例,那么在选择要销毁的内容时,它会选择其中最新的(与最旧的,这是预期的行为)?这可能是ActiveRecord还是MySQL的错误?
如果没有,是否有关于FactoryGirl或RSpec创建不代表生产的记录的方式?我怎样才能确定我的测试代表了真实的场景?