如何在 运行 rails 测试时覆盖 Date.today?
How to override Date.today when running rails tests?
我有一些测试在特定日期失败了,因为有人编写它们是为了使用 Date.today
。我想重现之前 select 日期的失败。
有没有办法 运行 rake test 使用 ENV 变量覆盖系统时钟?所以对 Date.today
、Time.now
、1.day.ago
和 1.day.from_now
的调用将使用我设置的日期?
喜欢,例如:
> DATE_TODAY='2017-01-04' rake test
对于测试,您可以使用timecop gem。
它为您提供了两种有用的方法 Timecop.freeze
和 Timecop.travel
.
比如可以使用freeze
静态设置时间在before hooks:
describe 'your tests' do
before do
Timecop.freeze(Time.new(2017, 1, 4))
end
after do
Timecop.return
end
it 'should do something' do
sleep(10)
Time.now # => 2017-01-04 00:00:00
end
end
或在块中:
Timecop.freeze(Time.now - 3.months) do
assert product.expired?
end
虽然使用travel
方法,你改变了开始时刻,但是时间还在流逝。
Timecop.travel(Time.new(2017, 1, 4))
sleep(10)
Time.now # => 2017-01-04 00:00:10
从 Rails 4.1 开始,您可以做到
travel_to Time.new(2004, 11, 24, 01, 04, 44)
完整的 API 文档在此处:http://api.rubyonrails.org/classes/ActiveSupport/Testing/TimeHelpers.html
我有一些测试在特定日期失败了,因为有人编写它们是为了使用 Date.today
。我想重现之前 select 日期的失败。
有没有办法 运行 rake test 使用 ENV 变量覆盖系统时钟?所以对 Date.today
、Time.now
、1.day.ago
和 1.day.from_now
的调用将使用我设置的日期?
喜欢,例如:
> DATE_TODAY='2017-01-04' rake test
对于测试,您可以使用timecop gem。
它为您提供了两种有用的方法 Timecop.freeze
和 Timecop.travel
.
比如可以使用freeze
静态设置时间在before hooks:
describe 'your tests' do
before do
Timecop.freeze(Time.new(2017, 1, 4))
end
after do
Timecop.return
end
it 'should do something' do
sleep(10)
Time.now # => 2017-01-04 00:00:00
end
end
或在块中:
Timecop.freeze(Time.now - 3.months) do
assert product.expired?
end
虽然使用travel
方法,你改变了开始时刻,但是时间还在流逝。
Timecop.travel(Time.new(2017, 1, 4))
sleep(10)
Time.now # => 2017-01-04 00:00:10
从 Rails 4.1 开始,您可以做到
travel_to Time.new(2004, 11, 24, 01, 04, 44)
完整的 API 文档在此处:http://api.rubyonrails.org/classes/ActiveSupport/Testing/TimeHelpers.html