【问题标题】:Django filter manytomany relationDjango过滤多对多关系
【发布时间】:2020-06-18 11:39:02
【问题描述】:

我花了很多时间试图过滤掉多对多相关的实体,但结果真的让我吃惊。我不明白如何解决这个问题以及为什么会发生这种情况。

我在 Django 中有 2 个模型:


class Application(models.Model):
    ...
    forms = models.ManyToManyField(Form, related_name='applications', through='ApplicationForm', blank=True)
    ...

class Form(models.Model):
    ...

class ApplicationForm(models.Model):
    application = models.ForeignKey(Application, on_delete=models.CASCADE)
    form = models.ForeignKey(Form, on_delete=models.CASCADE)
    created_at = models.DateTimeField()
    updated_at = models.DateTimeField(auto_now=True)

ApplicationSerializer 中,我想返回与我的应用程序相关的过滤表单。我尝试这样做:

forms = serializer.SerializerMethodField()

def get_forms(self, obj):
    qs = obj.forms.filter(status=Form.COMPLETED)
    return FormSerializer(qs, many=True, context=self.context).data

我有 2 个表格和 3 个应用程序,这两种表格都有。但是我的函数例如返回 6 种形式 [1, 2, 1, 2, 1, 2]。 我尝试对此进行调试,发现 obj.forms.all() 返回 2 个表单,但如果我添加过滤器,它返回 6。我尝试使用 obj.forms.filter(status=Form.COMPLETED).distinct() 但结果相同。

我无法创建像Forms.objects.filter(status=Form.COMPLETED).filter(pk__in=...) 这样的查询,因为我在应用程序管理器级别预取和注释了许多参数。所以我想知道有什么方法可以过滤与我的实例相关的多对多关系对象

【问题讨论】:

    标签: python django django-models django-rest-framework orm


    【解决方案1】:

    如果您的问题只是向用户显示数据,您可以处理此问题 在 to_represnataion 方法中。并修改您想要更改的数据。

        def to_representation(self, instance: Application):
            data = super().to_representation(instance)
            qs = obj.forms.filter(status=Form.COMPLETED)
            data['forms'] = FormSerializer(qs, many=True, context=self.context).data
            return data
    

    【讨论】:

    • 不,我对表示没有问题,主要问题是 obj.forms.filter(status=Form.COMPLETED) 例如返回 4 个实例而不是 2 个实例
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 2021-03-19
    • 2023-03-06
    • 2011-12-08
    • 1970-01-01
    • 2015-08-08
    • 2011-02-27
    相关资源
    最近更新 更多