|
1 | 1 | import contextlib |
2 | 2 |
|
| 3 | +from django.apps import apps |
3 | 4 | from django.core import checks |
4 | 5 | from django.core.exceptions import FieldDoesNotExist, ValidationError |
5 | 6 | from django.db import models |
6 | 7 | from django.db.models.fields.related import lazy_related_operation |
| 8 | +from django.utils.functional import cached_property |
7 | 9 |
|
8 | 10 | from .embedded_model import EmbeddedModelTransformFactory |
9 | | -from .utils import get_mongodb_connection |
| 11 | +from .utils import get_mongodb_connection, serialize_model_reference |
10 | 12 |
|
11 | 13 |
|
12 | 14 | class PolymorphicEmbeddedModelField(models.Field): |
@@ -80,7 +82,9 @@ def deconstruct(self): |
80 | 82 | "django_mongodb_backend.fields.polymorphic_embedded_model", |
81 | 83 | "django_mongodb_backend.fields", |
82 | 84 | ) |
83 | | - kwargs["embedded_models"] = self.embedded_models |
| 85 | + kwargs["embedded_models"] = tuple( |
| 86 | + serialize_model_reference(x) for x in self.embedded_models |
| 87 | + ) |
84 | 88 | del kwargs["editable"] |
85 | 89 | return name, path, args, kwargs |
86 | 90 |
|
@@ -158,11 +162,21 @@ def get_db_prep_save(self, embedded_instance, connection): |
158 | 162 | embedded_instance._state.adding = False |
159 | 163 | return field_values |
160 | 164 |
|
| 165 | + @cached_property |
| 166 | + def resolved_embedded_models(self): |
| 167 | + # Since Field.deconstruct() serializes self.embedded_models as a list |
| 168 | + # of strings, these strings may need to be resolved after a |
| 169 | + # Field.clone() in querying. |
| 170 | + return tuple( |
| 171 | + apps.get_model(model) if isinstance(model, str) else model |
| 172 | + for model in self.embedded_models |
| 173 | + ) |
| 174 | + |
161 | 175 | def get_transform(self, name): |
162 | 176 | transform = super().get_transform(name) |
163 | 177 | if transform: |
164 | 178 | return transform |
165 | | - for model in self.embedded_models: |
| 179 | + for model in self.resolved_embedded_models: |
166 | 180 | with contextlib.suppress(FieldDoesNotExist): |
167 | 181 | field = model._meta.get_field(name) |
168 | 182 | break |
|
0 commit comments