Как отфильтровать данные из модели parant на основе наличия отношений с дочерней моделью
У меня есть эти модели
class Tree(models.Model):
field = models.TextField()
class TaskProgress(models.Model):
base_task = models.ForeignKey(BaseTask, on_delete=models.CASCADE)
tree = models.ForeignKey(Tree, on_delete=models.CASCADE)
class BaseTask(models.Model):
trees=models.ManyToManyField(Tree, through='TaskProgress')
class TaskType1(BaseTask):
child1_field = models.TextField()
class TaskType2(BaseTask):
child2_field = models.TextField()
как получить весь прогресс задачи, связанный с TaskType2 ,
TaskProgress.objects.filter(???)
Я не думаю, что то, о чем вы спрашиваете, возможно, если модели разработаны так, как описано. Внешний ключ base_task указывает конкретно на BaseTask. Даже если TaskType1 и TaskType2 наследуются от BaseTask, они не имеют никакого отношения в базе данных. Они только выглядят похожими.
Вариант 1: Посмотрите на Generic Relations в Django. В принципе, это позволяет вам иметь отношение ForeignKey с более чем одним типом модели. Однако я бы не рекомендовал это делать. Общие отношения - это сплошной беспорядок, если вы не знаете, что делаете.
Вариант 2: Переосмыслите свою схему. Возможно, вы можете переместить отношение к двум TaskTypes вместо этого и обращаться к ним через related_name.
class TaskProgress(models.Model):
# base_task = models.ForeignKey(BaseTask, on_delete=models.CASCADE)
tree = models.ForeignKey(Tree, on_delete=models.CASCADE)
class TaskType1(BaseTask):
task_progress = models.OneToOneField(TaskProgress, related_name='task_type_1'
child1_field = models.TextField()
class TaskType2(BaseTask):
task_progress = models.OneToOneField(TaskProgress, related_name='task_type_2'
child2_field = models.TextField()
Таким образом вы создаете связь один-к-одному между TaskProgress и TaskType. Вы должны иметь возможность запрашивать то или другое, проверяя, существует ли связь, например, все экземпляры TaskProgress, имеющие связь с экземпляром TaskType1.
# Query all TaskProgress instances, that have a TaskType1
TaskProgress.objects.filter(task_type_1__isnull=False)
Я добавил дополнительное поле в класс BaseTask
TASK_TYPE =[('I','Irrigation'),('C','Care'),('A','Assessment'),('O','Other')]
class BaseTask(models.Model):
trees=models.ManyToManyField(Tree, through='TaskProgress')
worker = models.ManyToManyField(User)
task_type = models.CharField(max_length=1,choices=TASK_TYPE,null=True)
И фильтр будет выглядеть так
TaskProgress.objects.filter(base_task__task = "I")