You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

Django多表关联查询问题:多筛选条件获取关联表数据

Django外键关联表查询问题

我是Django新手,尝试从通过外键关联的两张表中获取数据。仅用service_id筛选时查询正常,但添加多条件筛选后无法正确获取数据,当前使用的查询语句如下:

processes = ServiceWorkOrder.objects.filter(service_id=service_id).filter(ServiceWorkOrder.workdata == WorkFlowOrder.id).select_related('workdata')

我的模型代码如下:

class WorkFlowOrder(AbstractModel):
    USER_TYPE = (
        ('SYSTEM', 'SYSTEM'),
        ('CUSTOMER', 'CUSTOMER'),
        ('AGENT', 'AGENT'),
        ('CUSTOMER_SUPPORT', 'CUSTOMER_SUPPORT')
    )
    id = models.IntegerField(primary_key=True)
    action_name = models.CharField(max_length=250)
    trigger_on_rejection = models.CharField(max_length=250)
    action_detail = models.CharField(max_length=500)  # in hours
    email_notification = models.BooleanField(default=False)
    sms_notification = models.BooleanField(default=False)
    mailer_notification = models.BooleanField(default=False)
    fax_notification = models.BooleanField(default=False)
    assignee = models.CharField(max_length=250, choices=USER_TYPE, null=True, default=None)
    notify_customer = models.BooleanField(default=False)
    notify_customer_support = models.BooleanField(default=False)

    class Meta:
        db_table = "WorkFlowOrder"

    def __str__(self):
        return 'WorkFlowOrder is %s action_name%s action_detail : %s' % (self.action_name, self.action_detail, self.id)


class ServiceWorkOrder(AbstractModel):
    service_id = models.CharField(max_length=250)
    workdata = models.ForeignKey(WorkFlowOrder, on_delete=models.CASCADE)
    generic_work_order_id = models.IntegerField(null=True, default=None)
    sequence_num = models.CharField(max_length=500)  # in hours
    email_template_id = models.IntegerField(null=True, default=None)
    sms_template_id = models.IntegerField(null=True, default=None)
    mailer_job_id = models.IntegerField(null=True, default=None)
    fax_template_id = models.IntegerField(null=True, default=None)
    dcg_email_template_id = models.IntegerField(null=True, default=None)

    class Meta:
        db_table = "ServiceWorkOrder"

解决方案

你添加的ServiceWorkOrder.workdata == WorkFlowOrder.id是错误的筛选写法,Django ORM不支持直接用模型类字段做这类比较。实际上ServiceWorkOrder的workdata外键本身就和WorkFlowOrder的id关联,这个关联是自动维护的,不需要额外声明。

场景1:仅获取指定service_id的关联数据

如果你的需求只是获取某个service_id对应的所有ServiceWorkOrder及其关联的WorkFlowOrder数据,直接执行以下查询即可:

processes = ServiceWorkOrder.objects.filter(service_id=service_id).select_related('workdata')

场景2:添加关联表字段的筛选条件

如果需要针对WorkFlowOrder的字段加筛选条件(比如筛选action_name为特定值),使用Django ORM的双下划线跨表查询语法:

# 示例:筛选service_id匹配,且关联的WorkFlowOrder的action_name为"Approval"的记录
processes = ServiceWorkOrder.objects.filter(
    service_id=service_id,
    workdata__action_name="Approval"
).select_related('workdata')

核心要点:

  • select_related('workdata')已经会自动执行关联查询,将WorkFlowOrder的数据一并取出,避免N+1查询问题。
  • 跨表筛选时必须用外键字段名__关联表字段名的格式,这是Django ORM的标准用法。

内容的提问来源于stack exchange,提问作者kshitij

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.07.15 07:05:06