Начиная с существующей ModelA.
Требования:
- в зависимости от ModelA.type, ModelA.example будет отношением к ModelB или Model C.
- предсуществующие Экземпляры ModelA необходимо инициализировать по умолчанию, в зависимости от ModelA.type (ModelA.type уже не обнуляется)
Текущее решение:
Я создал отношение generi c для ModelA:
class ModelA:
...
example_content_type = models.ForeignKey(ContentType, on_delete=models.CASCADE, null=True)
example_id = models.PositiveIntegerField(null=True)
example = GenericForeignKey("example_content_type", "example_id")
Я запустил ./manage.py makemigrations
, который создал миграцию с пустыми полями
Я изменил поля example_content_type
и example_id
на ненулевые
снова запустил makemigrations
и создал следующий пользовательский прогон Python перед автоматически сгенерированными изменениями:
def set_default_example(apps, schema_editor):
ModelA = apps.get_model("myExample", "ModelA")
all_model_a = ModelA.objects.all()
for model_a in all_model_a:
example = None
if model_a.type == "type_a":
example = ExampleForTypeA.objects.create(foo="foo")
if model_a.type == "type_b":
example = ExampleForTypeB.objects.create(bar="bar")
model_a.example = example
model_a.save()
попытка перенастроить это бросает с django.db.utils.IntegrityError: column "example_content_type_id" contains null values
Я вручную создал и присвоил content_type (работает, только если я назначил поле _id). он по-прежнему выдает: django.db.utils.IntegrityError: column "example_id" contains null values
, поэтому я вручную создал и присвоил example_id, получив следующий код:
def set_default_example(apps, schema_editor):
ModelA = apps.get_model("myExample", "ModelA")
all_model_a = ModelA.objects.all()
for model_a in all_model_a:
example = None
content_type = None
if model_a.type == "type_a":
example = ExampleForTypeA.objects.create(foo="foo")
content_type = ContentType.objects.get_for_model(ExampleForTypeA)
if model_a.type == "type_b":
example = ExampleForTypeB.objects.create(bar="bar")
content_type = ContentType.objects.get_for_model(ExampleForTypeB)
model_a.example_content_type_id = content_type.id
model_a.example_id = example.id
model_a.example = example
model_a.save()
Вопрос:
- Этот код работает, но мне кажется странным, что мне приходится вручную присваивать
example_content_type_id
и example_id
, это тот крайний случай, когда .save () не обрабатывает Generi c Relations?