【问题标题】:Sequelize Top level where with eagerly loaded models creates sub querySequelize Top level 使用热切加载的模型创建子查询
【发布时间】:2019-02-17 14:16:48
【问题描述】:

我遇到了一个问题,即 Sequelize 创建主模型的子查询,然后将包含项与该子查询连接,而不是直接与主模型表连接。包含的查询条件最终在子查询的 WHERE 子句中,这使其无效。我已经缩短了名称,希望能在不丢失任何相关信息的情况下保持紧凑。

环境: 节点:6.11.3 Sequelize:3.23.6 => 更新到 4.38.1 并且问题仍然存在 MySql:5.7.23

代码片段模型:

I.model:
   models.I.hasMany(models.II);
   models.I.belongsTo(models.CJ);
   models.I.belongsTo(models.CJS);
II.model:
   models.II.belongsTo(models.I);
CJ.model:
   models.CJ.hasMany(models.I);
   models.CJ.hasMany(models.CJS);
CJS.model:
    models.CJS.hasMany(models.I);

代码片段查询定义:

let where = { cId: '2',
iAmt: { '$gt': 0 },
'$or': 
 [ { '$CJ.a1$': {$like: '%246%'}} },
   { '$CJ.a2$': {$like: '%246%'} },
   { '$I.cPN$': {$like: '%246%'} } 
 ] };

 let query = {
   where: where,
   order: orderBy,
   distinct: true,
   offset: offset,
   limit: limit,
   include: [
   {
    model: CJ, 
    as: 'CJ',
    required: false
  }, {
    model: CJS, 
    as: 'CJS',
    required: false
  }, {
    model: II,
    as: 'IIs',
    required: false
  }
  ]
  };

  I.findAll(query)

产生如下 SQL:

SELECT `I`.*, `CJ`.`_id` AS `CJ._id`, `CJS`.`_id` AS `CJS._id`, `IIs`.`_id` AS `IIs._id`
FROM (SELECT `I`.`_id`, `I`.`CJId`, `I`.`CJSId`, `I`.`CId` 
  FROM `Is` AS `I` 
 WHERE `I`.`CId` = '2' AND 
       `I`.`iA` > 0 AND 
     (`CJ`.`a1` LIKE '%246%' OR 
      `CJ`.`a2` LIKE '%246%' OR 
      `I`.`cPN` LIKE '%246%'
     ) 
     ORDER BY `I`.`iNum` DESC LIMIT 0, 10) AS `I` 
     LEFT OUTER JOIN `CJs` AS `CJ` ON `I`.`CJId` = `CJ`.`_id` 
     LEFT OUTER JOIN `CJSs` AS `CJS` ON `I`.`CJSId` = `CJS`.`_id` 
     LEFT OUTER JOIN `IIs` AS `IIs` ON `I`.`_id` = `IIs`.`IId` 
     ORDER BY `I`.`iNum` DESC;

我期待这样的事情:

SELECT `I`.*, `CJ`.`_id` AS `CJ._id`, `CJS`.`_id` AS `CJS._id`, `IIs`.`_id` AS `IIs._id`
  FROM `Is` AS `I` 
     LEFT OUTER JOIN `CJs` AS `CJ` ON `I`.`CJId` = `CJ`.`_id` 
     LEFT OUTER JOIN `CJSs` AS `CJS` ON `I`.`CJSId` = `CJS`.`_id` 
     LEFT OUTER JOIN `IIs` AS `IIs` ON `I`.`_id` = `IIs`.`IId` 

WHERE `I`.`CId` = '2' AND 
       `I`.`iA` > 0 AND 
     (`CJ`.`a1` LIKE '%246%' OR 
      `CJ`.`a2` LIKE '%246%' OR 
      `I`.`cPN` LIKE '%246%'
) 
ORDER BY `I`.`iNum` DESC LIMIT 0, 10

如果我从包含中删除 II 模型,它确实可以工作并将 WHERE 移动到顶层。我承认这里的查询结构不是直截了当的,ICJCJS 的孩子,而 CJS 又是孩子CJ。然后III的孩子。我在这里想念什么?

Bueller 或任何人的 2 美分欢迎!

【问题讨论】:

    标签: subquery sequelize.js eager-loading


    【解决方案1】:

    这里发生的事情是因为您还使用了orderlimit 以及急切加载关联see the issue

    为了使它工作,有一个小技巧,你需要将subQuery: false 一起添加到你的根模型查询中

    let query = {
       where: where,
       order: orderBy,
       distinct: true,
       offset: offset,
       limit: limit,
       subQuery: false,
       include: [...]
    };
    

    【讨论】:

      猜你喜欢
      • 2015-06-03
      • 1970-01-01
      • 2014-05-21
      • 2023-03-25
      • 2014-01-05
      • 1970-01-01
      • 1970-01-01
      • 2019-08-10
      • 2014-07-09
      相关资源
      最近更新 更多