Django: Зависимость от заменяемой модели (ленивая ссылка)

Отказ от ответственности, я прочитал следующие сообщения, и они не дали полезного ответа для моего случая: lazy reference: doesn't provide model user?

django custom user model gives me lazy reference error

django-swappable-models

Я написал многократно используемое приложение, которое передает методы аутентификации и управление пользователями. В своем ядре оно переопределяет AUTH_USER_MODEL (назовем модель CustomUser) и предоставляет заменяемую модель Person, которая имеет поле O2O на CustomUser:

class CustomUser(AbstractUser):
    def save(self, *args, **kwargs):
        if not self.pk or hasattr(self, 'person') is False:
            super().save(*args, **kwargs)
            get_person_model().objects.create(birthdate=None, user=self)
        else:
            super().save(*args, **kwargs)

class AbstractPerson(models.Model):
    user = models.OneToOneField(settings.MY_APP_PERSON_MODEL, on_delete=models.SET_NULL, null=True, blank=True, related_name='person')
    
    birthdate = DateField(null=True, default=None)

    class Meta:
        abstract = True

class Person(AbstractPerson):
    
    class Meta(AbstractPerson.Meta):
        swappable = 'REUSABLE_APP_PERSON_MODEL'

Для создания миграций в моем многоразовом приложении я создал "фиктивный" проект django, который включает это приложение, и установил REUSABLE_APP_PERSON_MODEL в reusable_app.Person.

Это работает безупречно, в моем реальном проекте django я могу установить REUSABLE_APP_PERSON_MODEL в модель, которая наследуется от reusable_app.AbstractPerson.

Проблема возникает, когда у моего многоразового приложения есть другая модель, которая содержит внешний ключ к REUSABLE_APP_PERSON_MODEL:

class Invite(models.Model):
    email = models.EmailField()
    person = models.OneToOneField(settings.REUSABLE_APP_PERSON_MODEL, on_delete=models.CASCADE, null=False, related_name='+')
    code = models.CharField(max_length=5)

Снова я создал миграцию для этой модели в моем многократно используемом приложении, которое теперь имеет две миграции:

  1. Initial: Create CustomUser and Person model, where Person has set swappable in its options
  2. 0002: Create model Invite

Теперь у моего реального приложения django возникла проблема, я получаю следующую ошибку при создании начальной миграции:

ValueError: The field reusable_app.Invite.person was declared with a lazy reference to 'my_client_app.myperson', but app 'my_client_app' isn't installed.

Я подозреваю, что это происходит из-за следующего: makemigrations улавливает тот факт, что my_reusable_app уже имеет миграции. При их анализе становится ясно, что конкретная модель Person на самом деле определена в my_client_app. Но не существует миграции, которая фактически создала модель 'my_client_app.myperson'.

Если я удалю миграции (или, по крайней мере, миграцию, которая создает Invite модель из моего многоразового приложения), это работает, но я не думаю, что это правильное решение.

В документации django-swappable-models можно найти следующее:

В целом, пользователям вашей библиотеки не нужно вносить никаких подобных изменений в свои собственные скрипты миграции. Единственное исключение - если у вас имеете несколько уровней заменяемых моделей с внешними ключами, указывающими друг на друг на друга.

К сожалению, нет никаких указаний на то, что нужно делать в этом случае.

Любая помощь будет очень признательна.

Вернуться на верх