Django: Как осуществлять навигацию по многоуровневым обратным отношениям?
У меня есть несколько моделей, которые связаны иерархически:
- У проектов есть один или более экспериментов
- Эксперименты имеют один или более сканов
- Сканы имеют одно или более решений по сканированию
Если у меня есть конкретное решение о сканировании и я хочу получить проект, связанный с этим решением, как я могу это сделать?
В документации Django говорится о обратных отношениях, но примеры, похоже, ограничены одним уровнем отношений.
Например, чтобы получить ScanDecision, связанный с Scan, я могу сделать что-то вроде:
sd = ScanDecision.objects.get(id=1)
sd.scan_set.all() # Returns all scan objects related to the specific ScanDecision
Но что если я хочу получить Project, который связан с ScanDecision косвенно через Scan и Experiment?
например, что-то вроде этого, но без всех шагов?
sd = ScanDecision.objects.get(id=1) # The desired ScanDecision object
s = sd.scan_set.all() # Gets the related Scan object
e = s.experiment_set.all() # Gets the Experiment related to the selected Scan object
p = e.project_set.all() # Gets the Project related to the selected Experiment object
В идеале я хотел бы получить что-то вроде:
sd = ScanDecision.objects.get(id=1)
p = sd.project_set.all()
Примечание: Каждый объект знает только о своем непосредственно предшествующем объекте, например, отношения ForeignKey устанавливаются только между дочерним и родительским объектами, а не между любыми другими уровнями. Таким образом, ScanDecision имеет FK к Scan, но не к Experiment или Project. Аналогично, Scan имеет FK к Experiment, но не к Project.
Исходя из вашего обновления, вы можете использовать прямые отношения sd.scan.experiment.project. Чтобы ответить на вопрос, хотя для доступа к обратным отношениям вы можете сделать decisions = project.experiments.scans.decisions.all()