timeutils: fix newer/older comparison with TZ aware datetime

Blindly replacing the timezone information from a timestamp does not
make it correctly UTC. It just strips information away, and therefore
does not make any valid comparison.

This fixes the comparison function by normalizing the timestamps to UTC
before doing any comparison.

Change-Id: I3a1b1eae497200ca951ccb003dbcc75fb75380fa
This commit is contained in:
Julien Danjou 2015-06-03 15:50:11 +02:00
parent 421b562a85
commit 787b6e3e50
2 changed files with 16 additions and 6 deletions

View File

@ -112,6 +112,11 @@ class TimeUtilsTest(test_base.BaseTestCase):
self._test_is_older_than(lambda x: x.replace(
tzinfo=iso8601.iso8601.UTC))
def test_is_older_than_aware_no_utc(self):
self._test_is_older_than(lambda x: x.replace(
tzinfo=iso8601.iso8601.FixedOffset(1, 0, 'foo')).replace(
hour=7))
def _test_is_newer_than(self, fn):
strptime = datetime.datetime.strptime
with mock.patch('datetime.datetime') as datetime_mock:
@ -138,6 +143,11 @@ class TimeUtilsTest(test_base.BaseTestCase):
self._test_is_newer_than(lambda x: x.replace(
tzinfo=iso8601.iso8601.UTC))
def test_is_newer_than_aware_no_utc(self):
self._test_is_newer_than(lambda x: x.replace(
tzinfo=iso8601.iso8601.FixedOffset(1, 0, 'foo')).replace(
hour=7))
def test_set_time_override_using_default(self):
now = timeutils.utcnow_ts()

View File

@ -119,9 +119,9 @@ def normalize_time(timestamp):
def is_older_than(before, seconds):
"""Return True if before is older than seconds."""
if isinstance(before, six.string_types):
before = parse_isotime(before).replace(tzinfo=None)
else:
before = before.replace(tzinfo=None)
before = parse_isotime(before)
before = normalize_time(before)
return utcnow() - before > datetime.timedelta(seconds=seconds)
@ -129,9 +129,9 @@ def is_older_than(before, seconds):
def is_newer_than(after, seconds):
"""Return True if after is newer than seconds."""
if isinstance(after, six.string_types):
after = parse_isotime(after).replace(tzinfo=None)
else:
after = after.replace(tzinfo=None)
after = parse_isotime(after)
after = normalize_time(after)
return after - utcnow() > datetime.timedelta(seconds=seconds)