Sequelize findAndCountAll查询自动选中未指定字段问题
解决Sequelize findAndCountAll自动选中关联模型ID的问题
当用Sequelize的findAndCountAll写查询,关联Wallet和User模型时,框架会自动把User.id塞进查询字段里,逼你必须在group数组里加这个字段,最后分组结果完全不符合预期。
原问题代码示例
const result = await Wallet.findAndCountAll({ attributes: [ 'walletAddress', [sequelize.fn('COUNT', sequelize.col('Wallet.id')), 'transactionCount'] ], include: [ { model: User, attributes: [] // 明明没指定字段,还是自动选了User.id } ], group: ['walletAddress', 'User.id'], // 被迫加User.id,分组结果不对 raw: true });
自动生成的问题SQL
SELECT `Wallet`.`walletAddress`, COUNT(`Wallet`.`id`) AS `transactionCount`, `User`.`id` FROM `Wallets` AS `Wallet` LEFT OUTER JOIN `Users` AS `User` ON `Wallet`.`userId` = `User`.`id` GROUP BY `Wallet`.`walletAddress`, `User`.`id`;
修改后的正确代码
const result = await Wallet.findAndCountAll({ attributes: [ 'walletAddress', [sequelize.fn('COUNT', sequelize.col('Wallet.id')), 'transactionCount'] ], include: [ { model: User, attributes: [], // 明确不选User的任何字段 duplicating: false // 关键配置:阻止Sequelize自动添加关联模型的主键 } ], group: ['walletAddress'], // 只按需要的字段分组,去掉User.id raw: true, subQuery: false // 可选:如果有子查询问题,开启后用JOIN替代子查询 });
修改说明
duplicating: false:Sequelize默认会自动添加关联模型的主键来维护关联,哪怕你设了attributes: []。加这个配置就能阻止它把User.id塞进SELECT列表。- 移除
group里的User.id:现在查询不再选中这个字段,自然不需要再分组它,结果就符合预期了。 subQuery: false:如果你的查询因为子查询导致字段自动添加,开这个配置强制用JOIN,能进一步避免不必要的字段被选中。
修改后生成的正确SQL
SELECT `Wallet`.`walletAddress`, COUNT(`Wallet`.`id`) AS `transactionCount` FROM `Wallets` AS `Wallet` LEFT OUTER JOIN `Users` AS `User` ON `Wallet`.`userId` = `User`.`id` GROUP BY `Wallet`.`walletAddress`;
内容的提问来源于stack exchange,提问作者Scoopa
相关产品推荐
相关产品推荐

