Took into account DST when computing localtime zones. This wasn't ac… (#1258)

* Took into account DST when computing localtime zones.  This wasn't accounted for when using non-UTC datetimes with queue.enqueue_at()

* Updates tests with mocked timezones to test both scenarios
main
Evan Ackmann 5 years ago committed by GitHub
parent 91a22949c6
commit bd0fcc1a07
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23

@ -265,7 +265,7 @@ class ScheduledJobRegistry(BaseRegistry):
from datetime import timezone
except ImportError:
raise ValueError('datetime object with no timezone')
tz = timezone(timedelta(seconds=-time.timezone))
tz = timezone(timedelta(seconds=-(time.timezone if time.daylight == 0 else time.altzone)))
scheduled_datetime = scheduled_datetime.replace(tzinfo=tz)
timestamp = calendar.timegm(scheduled_datetime.utctimetuple())

@ -70,9 +70,38 @@ class TestScheduledJobRegistry(RQTestCase):
# If we pass in a datetime with no timezone, `schedule()`
# assumes local timezone so depending on your local timezone,
# the timestamp maybe different
registry.schedule(job, datetime(2019, 1, 1))
self.assertEqual(self.testconn.zscore(registry.key, job.id),
1546300800 + time.timezone) # 2019-01-01 UTC in Unix timestamp
# we need to account for the difference between a timezone
# with DST active and without DST active. The time.timezone
# property isn't accurate when time.daylight is non-zero,
# we'll test both.
# first, time.daylight == 0 (not in DST).
# mock the sitatuoin for American/New_York not in DST (UTC - 5)
# time.timezone = 18000
# time.daylight = 0
# time.altzone = 14400
mock_day = mock.patch('time.daylight', 0)
mock_tz = mock.patch('time.timezone', 18000)
mock_atz = mock.patch('time.altzone', 14400)
with mock_tz, mock_day, mock_atz:
registry.schedule(job, datetime(2019, 1, 1))
self.assertEqual(self.testconn.zscore(registry.key, job.id),
1546300800 + 18000) # 2019-01-01 UTC in Unix timestamp
# second, time.daylight != 0 (in DST)
# mock the sitatuoin for American/New_York not in DST (UTC - 4)
# time.timezone = 18000
# time.daylight = 1
# time.altzone = 14400
mock_day = mock.patch('time.daylight', 1)
mock_tz = mock.patch('time.timezone', 18000)
mock_atz = mock.patch('time.altzone', 14400)
with mock_tz, mock_day, mock_atz:
registry.schedule(job, datetime(2019, 1, 1))
self.assertEqual(self.testconn.zscore(registry.key, job.id),
1546300800 + 14400) # 2019-01-01 UTC in Unix timestamp
# Score is always stored in UTC even if datetime is in a different tz
tz = timezone(timedelta(hours=7))
@ -99,8 +128,8 @@ class TestScheduler(RQTestCase):
self.assertTrue(scheduler.should_reacquire_locks)
scheduler.acquire_locks()
self.assertIsNotNone(scheduler.lock_acquisition_time)
# scheduler.should_reacquire_locks always returns False if
# scheduler.should_reacquire_locks always returns False if
# scheduler.acquired_locks and scheduler._queue_names are the same
self.assertFalse(scheduler.should_reacquire_locks)
scheduler.lock_acquisition_time = datetime.now() - timedelta(minutes=16)
@ -251,7 +280,7 @@ class TestWorker(RQTestCase):
p.start()
queue.enqueue_at(datetime(2019, 1, 1, tzinfo=utc), say_hello)
worker.work(burst=False, with_scheduler=True)
worker.work(burst=False, with_scheduler=True)
p.join(1)
self.assertIsNotNone(worker.scheduler)
registry = FinishedJobRegistry(queue=queue)

Loading…
Cancel
Save