Monday, December 9, 2013

Change the Origin/Baseline Date with Timecop

Timecop provides a baseline for you to change the origin date and time called a "baseline", so that you can return to that origin instead of the real date and time. However, to use it, it provides a "return_to_baseline" method, and if you only want to do this temporarily to run all tests (even when using Timecop) to believe the day the tests were run on is a different day, you'd have to change all tests to use "return_to_baseline" instead of "return". Well, that is easy enough to circumvent. Here is code that let's your Rails tests always run as if it were Saturday, even though they are using "return" to return to what is assumed is today's date:

# Simulate tests running on Saturday to check for day of week issues.
Timecop.baseline = DateTime.now + (6 - Time.now.wday).days
class Timecop
  # return typically "unmock!"'s and goes back to real time, but we don't want that,
  # so make it act like return_to_baseline in class and instance.
  class << self; alias_method :return, :return_to_baseline; end
  alias_method :return, :return_to_baseline
end

Once you do that, there is no going back. You could alter it to alias_method the original return methods to undo it later, but just commenting/uncommenting that block works for me, since it is only for the rare situation that we have a test that only fails on one day of the week.

If you already make sure of baseline in your tests and use return_to_baseless, obviously don't redefine Timecop's return method like this. Redefining return may make it more difficult for the Timecop team to help you with support requests, so please use it only temporarily as needed, and don't say I didn't warn you.

No comments: