Ошибка импорта Django из внешнего ключа в другой модели приложения
Я следовал этому посту здесь и разобрался, как установить внешний ключ одной модели на модель в другом приложении. Однако, когда я пытаюсь сделать это во второй раз, я получаю ошибку и не знаю, почему.
У меня есть центральное приложение с моделями для "проекта" и "аннотации", а также приложение для отчетов с моделью отчета. У "аннотации" есть FK к "отчету" в приложении Reports, и это, кажется, хорошо работает с этим кодом:
#models.py for Central app
from GIanno.pt_reports.models import Report
class annotation(models.Model):
...
report=models.ForeignKey(Report)
Но в приложении Reports, когда я пытаюсь установить FK для "отчет", чтобы связать его с " проектом "из" Центрального "приложения, используя тот же формат, что и выше, я получаю ошибку" не удается импортировать имя "проект" из строки импорта.
Любые идеи о том, почему он работает так, а не иначе. Разве порядок имеет какое-то значение? Спасибо3 ответа:
Я предполагаю, что вы создали условие кругового импорта. Это происходит, когда вы импортируете что-то из одного модуля python, который, в свою очередь, импортирует из модуля, который пытается импортировать его, таким образом, предотвращая импорт от любого разрешения.
В общем случае существует три стратегии для работы с циклическим импортом, две из которых будут работать в этом случае:
Перемещайтесь по классам и импорту так, чтобы импорт шел только в одном направлении.
Использование ленивое вычисление. В случае Django это может быть выполнено для внешнего ключа путем передачи строки, указывающей имя приложения и модель с помощью точечной нотации:
report=models.ForeignKey('central.Report')
Переместите инструкцию import из области глобального модуля в область функции внутри модуля. Таким образом, импорт не оценивается сразу, и модуль может быть успешно импортирован в целом, все еще позволяя импорту в модуле произойти, когда он вызван. (Примечание: это не будет работать для ForeignKey Relations)
Ленивое разрешение FK (#2), вероятно, ваш лучший выбор здесь. В целом, хотя лучшая стратегия состоит в том, чтобы упростить расположение модели / модуля, чтобы избежать кругового импорта, когда это возможно.
Попробуйте:
class annotation(models.Model): ... report=models.ForeignKey('centralapp.Report')
Замените "centralapp" на имя вашего центрального приложения без необходимости импорта.
Другой сценарий, где ленивые отношения могут быть полезны, - это порядок импорта. Это не круговая ссылка (где он не может сказать, кто первый), а случай, когда один фрагмент кода загружается раньше, чем другой.
Например, предположим, что у меня есть модель Doc и модель журнала. Модель журнала имеет FK для Doc, поэтому я могу записывать изменения в документе. Это работает нормально, пока, скажем, я не попытаюсь создать запись журнала в методе сохранения для моей модели Doc (чтобы сделать событие сохранения запись журнала). В этом случае в объекте Doc отсутствует Log PK, но это аналогичная проблема.
В этом случае вы получаете проблему с порядком импорта, где нужно будет попытаться сослаться на что-то, что еще не было загружено в Python. Это похоже на круговую ссылку, но другая причина.
Это можно решить другими способами, но это еще один пример, где вы столкнетесь с этой проблемой.