Add this at the top of test/test_helper.rb (or elsewhere if not using rails):
# Extend the Time class so that we can offset the time that 'now' # returns. This should allow us to effectively time warp for functional # tests that require limits per hour, what not. class Time #:nodoc: class <<self attr_accessor :testing_offset alias_method :real_now, :now def now real_now - testing_offset end alias_method :new, :now end end Time.testing_offset = 0
Add this method to Test::Unit::TestCase (in the class definition in test_helper.rb):
# Time warp to the specified time for the duration of the passed block def pretend_now_is(time) begin Time.testing_offset = Time.now - time yield ensure Time.testing_offset = 0 end end
And now you can write time-based tests. For example:
def test_should_not_allow_more_than_3_requests_in_last_hour_from_same_ip (1..3).each { |n| successful_request } start_count = WorkOrderRequest.count post :new, :work_order_request => REQUEST_TEMPLATE assert_response :redirect assert_redirected_to :controller => 'work_order_request', :action => 'limit_exceeded' assert_equal start_count, WorkOrderRequest.count end def test_should_not_allow_more_than_10_requests_in_last_24_hours_from_same_ip 10.downto(1) do |n| pretend_now_is(n.hours.ago) do successful_request end end start_count = WorkOrderRequest.count post :new, :work_order_request => REQUEST_TEMPLATE assert_response :redirect assert_redirected_to :controller => 'work_order_request', :action => 'limit_exceeded' assert_equal start_count, WorkOrderRequest.count end