Django - Проблема с менеджером моделей - Запрос

Я все еще новичок и застрял в сложном для меня месте. Я не могу добиться того, чтобы данные из таблицы с внешним ключом "правильно" вставлялись в столбец ListView.

В основном я хочу создать представление списка в таблице (FeatureFilm). Это тоже работает. Но в одном столбце я получаю информацию из другой таблицы, а здесь я получаю данные, но не те, которые принадлежат конкретной строке таблицы.

Вот мои модели. Таблица, которую я хочу показать, это модель "FeatureFilm". Эта модель наследуется от моего базового класса Project "ProjectBaseModel". Затем есть еще одна таблица "CompanyInvolved Model". Она присоединена к таблице FeatureFilm с внешним ключом (feature_id).

Хранятся фильмы (FeatureFilm), и в процесс создания фильмов вовлечены различные компании. (CompanyInvolved)

class ProjectBaseModel(models.Model):
    title = models.CharField("Titel", max_length=100, blank=False, unique=True)

    leading_postproduction_id = models.ForeignKey(
        Company,
        verbose_name="Federführende Postproduktion",
        on_delete=models.SET_NULL,
        blank=True,
        null=True,
    )
    phase = models.CharField(choices=post_phase, max_length=30, blank=True, null=True)
    former_title = models.CharField("Titel, ehemalig", max_length=100, blank=True)
    title_international = models.CharField(
        "Titel, international", max_length=100, blank=True, null=True, unique=True
    )

class FeatureFilm(ProjectBaseModel):
    class Meta:
        verbose_name = "Kinofilm"
        verbose_name_plural = "Kinofilme"
        ordering = ["title"]

class ProductionManager(models.Manager):
    def get_production(self):
        return (
            super()
            .get_queryset()
            .filter(company_role="Produktion", is_production_list=True)
            .values_list("company_involved__name")
        )


class CompanyInvolved(models.Model):
    feature_id = models.ForeignKey(
        FeatureFilm,
        on_delete=models.CASCADE,
        null=True,
        blank=True,
    )
    tv_movie_id = models.ForeignKey(
        TvMovie, on_delete=models.CASCADE, null=True, blank=True
    )
    company_role = models.CharField(
        choices=company_role,
        max_length=15,
        blank=True,
        help_text="Produktion, Co-Produktion, Kinoverleiher, Sender, Weltvertrieb",
    )
    company_involved = models.ForeignKey(
        Company,
        on_delete=models.SET_NULL,
        null=True,
        blank=True,
    )


    is_production_list = models.BooleanField(
        default=False,
        verbose_name="Produktion in Liste",
    )
    productionmanager = ProductionManager()

    def __str__(self):
        return "#" + str(self.pk)

    class Meta:
        verbose_name = "Produktion, Co-Produktion, Verleih, Sender, Weltvertrieb"
        verbose_name_plural = "Produktion, Co-Produktion, Verleih, Sender, Weltvertrieb"
        ordering = ["pk"]

В основном я хотел генерировать вывод сейчас через шаблон. Я могу итерировать строки с помощью шаблона for loop. Но я также узнал, что более сложные запросы не работают в языке DjangoTemplate, или просто им там не место. Мне не нужны все строки данных из CompanyInvolved, а только company_role = "Production" и is_production_list = True. Комбинированный пункт "Where" в шаблоне сейчас хорош, но его не существует, поэтому я создал себе МЕНЕДЖЕР МОДЕЛИ (ProductionManager), который делает эту фильтрацию в модели.

вот вид:

class FeatureListView(LoginRequiredMixin, PermissionRequiredMixin, ListView):
    permission_required = "project.can_access_featurefilm_list"
    model = FeatureFilm
    template_name = "project/feature-list.html"

    def handle_no_permission(self):
        return redirect("access-denied")

здесь находится зависимый фрагмент в шаблоне:

              <tbody>

                {% for project in object_list %}
                    <tr>

                        <td><a href="{% url 'feature-detail-date' project.pk %}">{{ project.title }}</a></td>

                        <td>{{ project.companyinvolved_set.get_production }}
                        <br>
                        </td>
                        <td>{% if project.program_length_planned %}
                                {{ project.program_length_planned }}
                            {% endif %}
                        </td>
                        <td>{{ project.global_shooting_resolution }}</td>
                        <td>{{ project.global_resolution_theatrical }}</td>
                        <td>{% if project.hdr == 1%}
                                ja
                            {% else %}
                                nein
                            {% endif %}

                        </td>
                        <td>{{ project.stafflist.postproduction_supervisor_id.username }}</td>
                        <td>{% if project.phase %}
                            {{ project.phase }}
                            {% endif %}

                        </td>


                    </tr>

                  {% endfor %}
              </tbody>

Итак, я перебираю каждый кинопроект с помощью {% for project in object_list %} и затем я хочу показать в колонке "проблема" компанию, которая имеет роль production, а так как их может быть несколько, то ту, которая была ранее отмечена пользователем для просмотра списков - > is_production_list = TRue и тогда вывод должен получиться: {{ project.companyinvolved_set.get_production }}.

Результат движется в правильном направлении, но он все еще не окончательно корректен. Я получаю данные CompanyINvolved и они также отфильтрованы по company_role = "Production" и is_production_list = True , но эти значения теперь отображаются мне каждый раз в каждой отдельной строке одинаково, я получаю не по ROW связанных с ними производств, а просто каждый раз ВСЕ. Мне не хватает ссылки на объект FeatureFilm, но я не знаю, как теперь ее получить, или куда теперь эту ссылку поместить?

Я думаю, что ваш код не работает, потому что get_production вызывает super().get_queryset(), который возвращает новый QuerySet, без примененных фильтров, не основанный на Queryset в обратном поиске в companyinvolved_set

Я думаю, что лучше всего поместить эту логику либо в класс FeatureListView, либо в класс FeatureFilm, в зависимости от того, нужно ли вам повторно использовать этот вид поиска или нет.

Для FeatureListView вы можете переопределить get_queryset чем-то вроде этого (Здесь могут быть ошибки, я не могу проверить прямо сейчас):

class FeatureListView(LoginRequiredMixin, PermissionRequiredMixin, ListView):
    permission_required = "project.can_access_featurefilm_list"
    model = FeatureFilm
    template_name = "project/feature-list.html"

    def handle_no_permission(self):
        return redirect("access-denied")

        def get_queryset(self):
            return FeatureFilm.objects.annotate(
                    production_companies=FilteredRelation(
                    'company_involved', condition=(Q(company_involved__company_role='Production') & Q(company_involved__is_production_list=True))
                )
            ).all()

Тогда вы должны быть в состоянии перебирать производственные_компании в вашем шаблоне:

<td>{% for production in project.production_companies %}production.company_involved.name{% endfor %}</td>
Вернуться на верх