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

如何在Sequelize中查询关联表是否存在记录并返回标识

问题描述

我有一个ModelA模型,与ModelB模型存在一对多(1:N)关联。我想要获取ModelA的所有记录,同时返回一个布尔值:若存在至少一条关联的ModelB记录则为true,否则为false。

关联关系定义如下:

ModelA.hasMany(ModelB)
ModelB.belongsTo(ModelA)

当前使用的查询语句:

const results = await ModelA.findAll({
  include: { model: ModelB, required: false }
})

该方式通过左外连接(outer join)可获取存在的ModelB匹配记录,但我并不关心ModelB的具体记录,仅需知道其是否存在。是否有办法生成对应的SELECT查询语句,直接根据连接结果返回true/false?

我期望的查询语句如下:

SELECT a.*, CASE WHEN b.id IS NOT NULL THEN true ELSE false END
FROM modelA a LEFT OUTER JOIN modelB b on b.model_a_id = a.id
解决方案

方法一:用literal实现你期望的CASE逻辑

通过在查询的attributes中添加自定义字段,结合sequelize.literal生成目标SQL,同时分组避免左连接导致的重复记录:

const results = await ModelA.findAll({
  attributes: [
    // 保留ModelA的所有字段
    ...Object.keys(ModelA.rawAttributes).map(key => `ModelA.${key}`),
    // 生成布尔字段hasModelB
    [sequelize.literal('CASE WHEN "ModelB"."id" IS NOT NULL THEN true ELSE false END'), 'hasModelB']
  ],
  include: {
    model: ModelB,
    required: false,
    attributes: [] // 不加载ModelB的任何字段
  },
  group: ['ModelA.id'] // 按ModelA主键分组,去重
})

方法二:用EXISTS子查询(性能更优)

左连接会返回匹配的ModelB记录再去重,而EXISTS只需判断是否存在关联记录,性能更高效:

const results = await ModelA.findAll({
  attributes: [
    ...Object.keys(ModelA.rawAttributes).map(key => `ModelA.${key}`),
    [sequelize.literal('EXISTS(SELECT 1 FROM "ModelB" WHERE "ModelB"."model_a_id" = "ModelA"."id")'), 'hasModelB']
  ]
})

对应的SQL为:

SELECT "ModelA".*, EXISTS(SELECT 1 FROM "ModelB" WHERE "ModelB"."model_a_id" = "ModelA"."id") AS "hasModelB" FROM "ModelA";

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.06.30 19:16:13