test_timezone.py 8.5 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206
  1. import datetime
  2. import pickle
  3. from unittest import mock
  4. import pytz
  5. from django.test import SimpleTestCase, override_settings
  6. from django.utils import timezone
  7. CET = pytz.timezone("Europe/Paris")
  8. EAT = timezone.get_fixed_timezone(180) # Africa/Nairobi
  9. ICT = timezone.get_fixed_timezone(420) # Asia/Bangkok
  10. class TimezoneTests(SimpleTestCase):
  11. def test_now(self):
  12. with override_settings(USE_TZ=True):
  13. self.assertTrue(timezone.is_aware(timezone.now()))
  14. with override_settings(USE_TZ=False):
  15. self.assertTrue(timezone.is_naive(timezone.now()))
  16. def test_localdate(self):
  17. naive = datetime.datetime(2015, 1, 1, 0, 0, 1)
  18. with self.assertRaisesMessage(ValueError, 'localtime() cannot be applied to a naive datetime'):
  19. timezone.localdate(naive)
  20. with self.assertRaisesMessage(ValueError, 'localtime() cannot be applied to a naive datetime'):
  21. timezone.localdate(naive, timezone=EAT)
  22. aware = datetime.datetime(2015, 1, 1, 0, 0, 1, tzinfo=ICT)
  23. self.assertEqual(timezone.localdate(aware, timezone=EAT), datetime.date(2014, 12, 31))
  24. with timezone.override(EAT):
  25. self.assertEqual(timezone.localdate(aware), datetime.date(2014, 12, 31))
  26. with mock.patch('django.utils.timezone.now', return_value=aware):
  27. self.assertEqual(timezone.localdate(timezone=EAT), datetime.date(2014, 12, 31))
  28. with timezone.override(EAT):
  29. self.assertEqual(timezone.localdate(), datetime.date(2014, 12, 31))
  30. def test_override(self):
  31. default = timezone.get_default_timezone()
  32. try:
  33. timezone.activate(ICT)
  34. with timezone.override(EAT):
  35. self.assertIs(EAT, timezone.get_current_timezone())
  36. self.assertIs(ICT, timezone.get_current_timezone())
  37. with timezone.override(None):
  38. self.assertIs(default, timezone.get_current_timezone())
  39. self.assertIs(ICT, timezone.get_current_timezone())
  40. timezone.deactivate()
  41. with timezone.override(EAT):
  42. self.assertIs(EAT, timezone.get_current_timezone())
  43. self.assertIs(default, timezone.get_current_timezone())
  44. with timezone.override(None):
  45. self.assertIs(default, timezone.get_current_timezone())
  46. self.assertIs(default, timezone.get_current_timezone())
  47. finally:
  48. timezone.deactivate()
  49. def test_override_decorator(self):
  50. default = timezone.get_default_timezone()
  51. @timezone.override(EAT)
  52. def func_tz_eat():
  53. self.assertIs(EAT, timezone.get_current_timezone())
  54. @timezone.override(None)
  55. def func_tz_none():
  56. self.assertIs(default, timezone.get_current_timezone())
  57. try:
  58. timezone.activate(ICT)
  59. func_tz_eat()
  60. self.assertIs(ICT, timezone.get_current_timezone())
  61. func_tz_none()
  62. self.assertIs(ICT, timezone.get_current_timezone())
  63. timezone.deactivate()
  64. func_tz_eat()
  65. self.assertIs(default, timezone.get_current_timezone())
  66. func_tz_none()
  67. self.assertIs(default, timezone.get_current_timezone())
  68. finally:
  69. timezone.deactivate()
  70. def test_override_string_tz(self):
  71. with timezone.override('Asia/Bangkok'):
  72. self.assertEqual(timezone.get_current_timezone_name(), 'Asia/Bangkok')
  73. def test_override_fixed_offset(self):
  74. with timezone.override(timezone.FixedOffset(0, 'tzname')):
  75. self.assertEqual(timezone.get_current_timezone_name(), 'tzname')
  76. def test_activate_invalid_timezone(self):
  77. with self.assertRaisesMessage(ValueError, 'Invalid timezone: None'):
  78. timezone.activate(None)
  79. def test_is_aware(self):
  80. self.assertTrue(timezone.is_aware(datetime.datetime(2011, 9, 1, 13, 20, 30, tzinfo=EAT)))
  81. self.assertFalse(timezone.is_aware(datetime.datetime(2011, 9, 1, 13, 20, 30)))
  82. def test_is_naive(self):
  83. self.assertFalse(timezone.is_naive(datetime.datetime(2011, 9, 1, 13, 20, 30, tzinfo=EAT)))
  84. self.assertTrue(timezone.is_naive(datetime.datetime(2011, 9, 1, 13, 20, 30)))
  85. def test_make_aware(self):
  86. self.assertEqual(
  87. timezone.make_aware(datetime.datetime(2011, 9, 1, 13, 20, 30), EAT),
  88. datetime.datetime(2011, 9, 1, 13, 20, 30, tzinfo=EAT))
  89. with self.assertRaises(ValueError):
  90. timezone.make_aware(datetime.datetime(2011, 9, 1, 13, 20, 30, tzinfo=EAT), EAT)
  91. def test_make_naive(self):
  92. self.assertEqual(
  93. timezone.make_naive(datetime.datetime(2011, 9, 1, 13, 20, 30, tzinfo=EAT), EAT),
  94. datetime.datetime(2011, 9, 1, 13, 20, 30))
  95. self.assertEqual(
  96. timezone.make_naive(datetime.datetime(2011, 9, 1, 17, 20, 30, tzinfo=ICT), EAT),
  97. datetime.datetime(2011, 9, 1, 13, 20, 30))
  98. with self.assertRaisesMessage(ValueError, 'make_naive() cannot be applied to a naive datetime'):
  99. timezone.make_naive(datetime.datetime(2011, 9, 1, 13, 20, 30), EAT)
  100. def test_make_naive_no_tz(self):
  101. self.assertEqual(
  102. timezone.make_naive(datetime.datetime(2011, 9, 1, 13, 20, 30, tzinfo=EAT)),
  103. datetime.datetime(2011, 9, 1, 5, 20, 30)
  104. )
  105. def test_make_aware_no_tz(self):
  106. self.assertEqual(
  107. timezone.make_aware(datetime.datetime(2011, 9, 1, 13, 20, 30)),
  108. datetime.datetime(2011, 9, 1, 13, 20, 30, tzinfo=timezone.get_fixed_timezone(-300))
  109. )
  110. def test_make_aware2(self):
  111. self.assertEqual(
  112. timezone.make_aware(datetime.datetime(2011, 9, 1, 12, 20, 30), CET),
  113. CET.localize(datetime.datetime(2011, 9, 1, 12, 20, 30)))
  114. with self.assertRaises(ValueError):
  115. timezone.make_aware(CET.localize(datetime.datetime(2011, 9, 1, 12, 20, 30)), CET)
  116. def test_make_aware_pytz(self):
  117. self.assertEqual(
  118. timezone.make_naive(CET.localize(datetime.datetime(2011, 9, 1, 12, 20, 30)), CET),
  119. datetime.datetime(2011, 9, 1, 12, 20, 30))
  120. self.assertEqual(
  121. timezone.make_naive(
  122. pytz.timezone("Asia/Bangkok").localize(datetime.datetime(2011, 9, 1, 17, 20, 30)), CET
  123. ),
  124. datetime.datetime(2011, 9, 1, 12, 20, 30))
  125. with self.assertRaisesMessage(ValueError, 'make_naive() cannot be applied to a naive datetime'):
  126. timezone.make_naive(datetime.datetime(2011, 9, 1, 12, 20, 30), CET)
  127. def test_make_aware_pytz_ambiguous(self):
  128. # 2:30 happens twice, once before DST ends and once after
  129. ambiguous = datetime.datetime(2015, 10, 25, 2, 30)
  130. with self.assertRaises(pytz.AmbiguousTimeError):
  131. timezone.make_aware(ambiguous, timezone=CET)
  132. std = timezone.make_aware(ambiguous, timezone=CET, is_dst=False)
  133. dst = timezone.make_aware(ambiguous, timezone=CET, is_dst=True)
  134. self.assertEqual(std - dst, datetime.timedelta(hours=1))
  135. self.assertEqual(std.tzinfo.utcoffset(std), datetime.timedelta(hours=1))
  136. self.assertEqual(dst.tzinfo.utcoffset(dst), datetime.timedelta(hours=2))
  137. def test_make_aware_pytz_non_existent(self):
  138. # 2:30 never happened due to DST
  139. non_existent = datetime.datetime(2015, 3, 29, 2, 30)
  140. with self.assertRaises(pytz.NonExistentTimeError):
  141. timezone.make_aware(non_existent, timezone=CET)
  142. std = timezone.make_aware(non_existent, timezone=CET, is_dst=False)
  143. dst = timezone.make_aware(non_existent, timezone=CET, is_dst=True)
  144. self.assertEqual(std - dst, datetime.timedelta(hours=1))
  145. self.assertEqual(std.tzinfo.utcoffset(std), datetime.timedelta(hours=1))
  146. self.assertEqual(dst.tzinfo.utcoffset(dst), datetime.timedelta(hours=2))
  147. def test_get_default_timezone(self):
  148. self.assertEqual(timezone.get_default_timezone_name(), 'America/Chicago')
  149. def test_get_default_timezone_utc(self):
  150. with override_settings(USE_TZ=True, TIME_ZONE='UTC'):
  151. self.assertIs(timezone.get_default_timezone(), timezone.utc)
  152. def test_fixedoffset_timedelta(self):
  153. delta = datetime.timedelta(hours=1)
  154. self.assertEqual(timezone.get_fixed_timezone(delta).utcoffset(''), delta)
  155. def test_fixedoffset_negative_timedelta(self):
  156. delta = datetime.timedelta(hours=-2)
  157. self.assertEqual(timezone.get_fixed_timezone(delta).utcoffset(''), delta)
  158. def test_fixedoffset_pickle(self):
  159. self.assertEqual(pickle.loads(pickle.dumps(timezone.FixedOffset(0, 'tzname'))).tzname(''), 'tzname')