Skip to content

Commit c5cf303

Browse files
committed
Support encoder and decoder in jsonfield.
1 parent 9173812 commit c5cf303

File tree

5 files changed

+18
-17
lines changed

5 files changed

+18
-17
lines changed

django_mongodb/base.py

Lines changed: 0 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -138,7 +138,6 @@ def _connect(self):
138138
self.connection = MongoClient(
139139
host=settings_dict["HOST"] or None,
140140
port=int(settings_dict["PORT"] or 27017),
141-
uuidRepresentation="standard",
142141
**options,
143142
)
144143
db_name = settings_dict["NAME"]

django_mongodb/features.py

Lines changed: 1 addition & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -43,7 +43,7 @@ class DatabaseFeatures(BaseDatabaseFeatures):
4343
"lookup.tests.LookupTests.test_exact_sliced_queryset_limit_one",
4444
"lookup.tests.LookupTests.test_exact_sliced_queryset_limit_one_offset",
4545
# Regex lookup doesn't work on json fields.
46-
"model_fields.test_jsonfield.TestQuerying.test_icontains"
46+
"model_fields.test_jsonfield.TestQuerying.test_icontains",
4747
# MongoDB gives the wrong result of log(number, base) when base is a
4848
# fractional Decimal: https://jira.mongodb.org/browse/SERVER-91223
4949
"db_functions.math.test_log.LogTests.test_decimal",
@@ -418,10 +418,6 @@ def django_test_expected_failures(self):
418418
"db_functions.comparison.test_cast.CastTests.test_cast_from_python_to_datetime",
419419
"db_functions.comparison.test_cast.CastTests.test_cast_to_duration",
420420
},
421-
"Mongodb support uuid as a type in json fields.": {
422-
"model_fields.test_jsonfield.JSONFieldTests.test_invalid_value",
423-
"model_fields.test_jsonfield.JSONFieldTests.test_db_check_constraints",
424-
},
425421
"Mongodb's Null behaviour is different from sql's": {
426422
"model_fields.test_jsonfield.TestQuerying.test_expression_wrapper_key_transform",
427423
"model_fields.test_jsonfield.TestSaveLoad.test_json_null_different_from_sql_null",
@@ -430,7 +426,6 @@ def django_test_expected_failures(self):
430426
"model_fields.test_jsonfield.TestQuerying.test_none_key",
431427
"model_fields.test_jsonfield.TestQuerying.test_none_key_exclude",
432428
},
433-
"Pipeline filtering": {"model_fields.test_jsonfield.TestQuerying.test_icontains"},
434429
}
435430

436431
@cached_property

django_mongodb/fields/json_field.py

Lines changed: 10 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -1,3 +1,5 @@
1+
import json
2+
13
from django.db import NotSupportedError
24
from django.db.models import JSONField
35
from django.db.models.fields.json import (
@@ -31,13 +33,13 @@ def data_contains(self, compiler, connection): # noqa: ARG001
3133

3234
def from_db_value(self, value, expression, connection):
3335
"""
34-
MongoDB does not need to change the json value. It is stored as it is.
36+
Transforms the value retrieved from the database into a string if the database
37+
vendor is MongoDB. This is necessary because MongoDB saves the data as a
38+
dictionary, and converting it to a JSON string allows for proper decoding.
3539
"""
36-
return (
37-
value
38-
if connection.vendor == "mongodb"
39-
else _from_db_value(self, value, expression, connection)
40-
)
40+
if connection.vendor == "mongodb":
41+
value = json.dumps(value)
42+
return _from_db_value(self, value, expression, connection)
4143

4244

4345
def has_key_lookup(self, compiler, connection):
@@ -62,7 +64,7 @@ def has_key_lookup(self, compiler, connection):
6264
return {self.mongo_operator: keys}
6365

6466

65-
__process_rhs = JSONExact.process_rhs
67+
_process_rhs = JSONExact.process_rhs
6668

6769

6870
def json_process_rhs(self, compiler, connection):
@@ -73,7 +75,7 @@ def json_process_rhs(self, compiler, connection):
7375
return (
7476
super(JSONExact, self).process_rhs(compiler, connection)
7577
if connection.vendor == "mongodb"
76-
else __process_rhs(self, compiler, connection)
78+
else _process_rhs(self, compiler, connection)
7779
)
7880

7981

django_mongodb/lookups.py

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -4,7 +4,7 @@
44
BuiltinLookup,
55
FieldGetDbPrepValueIterableMixin,
66
IsNull,
7-
PatternLookup
7+
PatternLookup,
88
UUIDTextMixin,
99
)
1010

django_mongodb/operations.py

Lines changed: 6 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,9 +1,11 @@
11
import datetime
2+
import json
23
import re
34
import uuid
45

56
from bson.decimal128 import Decimal128
67
from django.conf import settings
8+
from django.db import DataError
79
from django.db.backends.base.operations import BaseDatabaseOperations
810
from django.db.models.expressions import Combinable
911
from django.utils import timezone
@@ -50,7 +52,10 @@ def adapt_decimalfield_value(self, value, max_digits=None, decimal_places=None):
5052
return Decimal128(value)
5153

5254
def adapt_json_value(self, value, encoder):
53-
return value
55+
try:
56+
return json.loads(json.dumps(value, cls=encoder))
57+
except json.decoder.JSONDecodeError as e:
58+
raise DataError from e
5459

5560
def adapt_timefield_value(self, value):
5661
"""Store TimeField as datetime."""

0 commit comments

Comments
 (0)