Skip to content

Commit 78fd337

Browse files
committed
rework time zone support to set DatabaseFeatures.supports_timezones = False
Previously, incorrect values were stored in the database.
1 parent fa3ef6e commit 78fd337

File tree

3 files changed

+18
-9
lines changed

3 files changed

+18
-9
lines changed

django_mongodb/base.py

Lines changed: 0 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -145,7 +145,6 @@ def _connect(self):
145145
self.connection = MongoClient(
146146
host=settings_dict["HOST"] or None,
147147
port=int(settings_dict["PORT"] or 27017),
148-
tz_aware=True,
149148
**options,
150149
)
151150
db_name = settings_dict["NAME"]

django_mongodb/features.py

Lines changed: 4 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -7,6 +7,8 @@ class DatabaseFeatures(BaseDatabaseFeatures):
77
supports_ignore_conflicts = False
88
# Not implemented: https://github.com/mongodb-labs/django-mongodb/issues/8
99
supports_json_field = False
10+
# MongoDB stores datetimes in UTC.
11+
supports_timezones = False
1012
# Not implemented: https://github.com/mongodb-labs/django-mongodb/issues/7
1113
supports_transactions = False
1214
uses_savepoints = False
@@ -20,7 +22,6 @@ class DatabaseFeatures(BaseDatabaseFeatures):
2022
"basic.tests.ModelLookupTest.test_does_not_exist",
2123
"basic.tests.ModelLookupTest.test_equal_lookup",
2224
"basic.tests.ModelLookupTest.test_rich_lookup",
23-
"basic.tests.ModelTest.test_year_lookup_edge_case",
2425
"lookup.tests.LookupTests.test_chain_date_time_lookups",
2526
"lookup.test_timefield.TimeFieldLookupTests.test_hour_lookups",
2627
"lookup.test_timefield.TimeFieldLookupTests.test_minute_lookups",
@@ -286,8 +287,8 @@ class DatabaseFeatures(BaseDatabaseFeatures):
286287
"timezones.tests.LegacyDatabaseTests.test_cursor_execute_accepts_naive_datetime",
287288
"timezones.tests.LegacyDatabaseTests.test_cursor_execute_returns_naive_datetime",
288289
"timezones.tests.LegacyDatabaseTests.test_raw_sql",
289-
"timezones.tests.NewDatabaseTests.test_cursor_execute_accepts_aware_datetime",
290-
"timezones.tests.NewDatabaseTests.test_cursor_execute_returns_aware_datetime",
290+
"timezones.tests.NewDatabaseTests.test_cursor_execute_accepts_naive_datetime",
291+
"timezones.tests.NewDatabaseTests.test_cursor_execute_returns_naive_datetime",
291292
"timezones.tests.NewDatabaseTests.test_cursor_explicit_time_zone",
292293
"timezones.tests.NewDatabaseTests.test_raw_sql",
293294
},

django_mongodb/operations.py

Lines changed: 14 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -17,8 +17,16 @@ def adapt_datefield_value(self, value):
1717
return datetime.datetime.combine(value, datetime.datetime.min.time())
1818

1919
def adapt_datetimefield_value(self, value):
20-
if not settings.USE_TZ and value is not None and timezone.is_naive(value):
21-
value = timezone.make_aware(value)
20+
if value is None:
21+
return None
22+
if timezone.is_aware(value):
23+
if settings.USE_TZ:
24+
value = timezone.make_naive(value, self.connection.timezone)
25+
else:
26+
raise ValueError(
27+
"MongoDB backend does not support timezone-aware "
28+
"datetimes when USE_TZ is False."
29+
)
2230
return value
2331

2432
def adapt_decimalfield_value(self, value, max_digits=None, decimal_places=None):
@@ -31,6 +39,8 @@ def adapt_timefield_value(self, value):
3139
"""Store TimeField as datetime."""
3240
if value is None:
3341
return None
42+
if timezone.is_aware(value):
43+
raise ValueError("MongoDB backend does not support timezone-aware times.")
3444
return datetime.datetime.combine(datetime.datetime.min.date(), value)
3545

3646
def get_db_converters(self, expression):
@@ -39,7 +49,7 @@ def get_db_converters(self, expression):
3949
if internal_type == "DateField":
4050
converters.append(self.convert_datefield_value)
4151
elif internal_type == "DateTimeField":
42-
if not settings.USE_TZ:
52+
if settings.USE_TZ:
4353
converters.append(self.convert_datetimefield_value)
4454
elif internal_type == "DecimalField":
4555
converters.append(self.convert_decimalfield_value)
@@ -56,8 +66,7 @@ def convert_datefield_value(self, value, expression, connection):
5666

5767
def convert_datetimefield_value(self, value, expression, connection):
5868
if value is not None:
59-
# Django expects naive datetimes when settings.USE_TZ is False.
60-
value = timezone.make_naive(value)
69+
value = timezone.make_aware(value, self.connection.timezone)
6170
return value
6271

6372
def convert_decimalfield_value(self, value, expression, connection):

0 commit comments

Comments
 (0)