question-mark
Stuck on an issue?

Lightrun Answers was designed to reduce the constant googling that comes with debugging 3rd party libraries. It collects links to all the places you might be looking at while hunting down a tough bug.

And, if you’re still stuck at the end, we’re happy to hop on a call to see how we can help out.

Sequelize association count producing incorrect SQL and results

See original GitHub issue

With the following query:

models.School.findOne({
  where: { id },
  include: [{ attributes: [], model: models.Teacher }, { attributes: [], model: models.Pupil }],
  attributes: [
    'School.*',
    [Sequelize.fn('COUNT', Sequelize.col('Teachers.id')), 'teachers'],
    [Sequelize.fn('COUNT', Sequelize.col('Pupils.id')), 'pupils']
  ]
})

In the model definitions I have a belongsTo/haveMany association set up e.g.:

School.hasMany(models.Teacher, {
  foreignKey: 'schoolId',
  allowNull: false
});

School.hasMany(models.Pupil, {
  foreignKey: 'schoolId',
  allowNull: false
});
Teacher.belongsTo(models.School, {
  foreignKey: 'schoolId',
  allowNull: false
});
Pupil.belongsTo(models.School, {
  foreignKey: 'schoolId',
  allowNull: false
});

The SQL that gets produced is:

SELECT `School`.`id`,
`School`.*,
COUNT(`Teachers`.`id`) AS `teachers`,
COUNT(`Pupils`.`id`) AS `pupils` 
FROM `Schools` AS `School`
LEFT OUTER JOIN `Teachers` AS `Teachers` ON `School`.`id` = `Teachers`.`school_id` AND `Teachers`.`deletedAt` IS NULL 
LEFT OUTER JOIN `Pupils` AS `Pupils` ON `School`.`id` = `Pupils`.`school_id` AND `Pupils`.`deletedAt` IS NULL 
WHERE (`School`.`deletedAt` IS NULL AND `School`.`id` = '34fa61f7-d078-4560-a81d-4351d5ce5179');

If I run this query in my app, all I get back is an object like this:

{
    teachers: 200,
    pupils: 200
}

However if I run this in my SQL app I get back the row with all fields for a school, but I get two ID columns. The other thing is there is only 100 pupils and 2 teachers associated with that school (and I can confirm this by running a single count against the table directly with the above school_id).

Any ideas?

Issue Analytics

  • State:closed
  • Created 7 years ago
  • Comments:5 (2 by maintainers)

github_iconTop GitHub Comments

7reactions
tanepipercommented, May 26, 2016

Fixed: Had to do this:

models.School.findOne({
        where: { id },
        include: [{ attributes: [], model: models.Teacher }, { attributes: [], model: models.Pupil }],
        attributes: {
          include: [
            [Sequelize.fn('COUNT', Sequelize.fn('DISTINCT', Sequelize.col('Teachers.id'))), 'teachers'],
            [Sequelize.fn('COUNT', Sequelize.fn('DISTINCT', Sequelize.col('Pupils.id'))), 'pupils']
          ]
        }
      })
0reactions
janmeiercommented, May 26, 2016

There is no way to do that I think - because it would break the limit - you would be limiting the number of rows from the cartesian join, not the number of schools.

You can maybe try adding the counts to the includes for teacher and pupil - Not sure if it will work, but that will at least remove them from the inner query

Read more comments on GitHub >

github_iconTop Results From Across the Web

Counting associated entries with Sequelize
Using Sequelize, how do I get all entries from locations and total count of entries in sensors that are associated with each entry...
Read more >
Sub Queries
Now, we are ready for examples of the power of subqueries. Let's say we wanted to compute via SQL a laughReactionsCount for each...
Read more >
The Comprehensive Sequelize Cheatsheet
Sequelize is the most famous Node ORM and is quite feature-rich, ... --save sqlite3 npm install --save tedious # Microsoft SQL Server ...
Read more >
sequelize query use column name instead model name
2 apps and 19,500,000 results ... How to implement many to many association in sequelize ... the SQL builder creates incorrect SQL for...
Read more >
Sequelize - how to COUNT table rows number with code ...
Sequelize Model.count() method is used to generate and execute a SELECT COUNT SQL query to your connected database.
Read more >

github_iconTop Related Medium Post

No results found

github_iconTop Related StackOverflow Question

No results found

github_iconTroubleshoot Live Code

Lightrun enables developers to add logs, metrics and snapshots to live code - no restarts or redeploys required.
Start Free

github_iconTop Related Reddit Thread

No results found

github_iconTop Related Hackernoon Post

No results found

github_iconTop Related Tweet

No results found

github_iconTop Related Dev.to Post

No results found

github_iconTop Related Hashnode Post

No results found