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.

Incorrect SELECT query generation including "LIMIT" clause and "M:N" association with "where" clause returns unexpected results

See original GitHub issue

Hello,

I’ve come across a bug with query generation which include limiting results with including belongsToMany relation containing WHERE clause.

I made executable script to demonstrate this behavior as they are cases when generated query might return expected result if query and data in database are in specific state.

if you investigate the file the following are queries generated for particular demonstration cases:

“Test 1”: Works

    Student.findAndCount({
        offset: 6,
        order: [["id", "DESC"]],
        include: [
            {
                model: Teacher,
                as: 'teachers',
                where: {
                    id: {$in: [3, 2]}
                }
            }
        ]
    });
SELECT "student"."id", "student"."age", "student"."name",
"student"."created_at", "student"."updated_at", "teachers"."id" AS
"teachers.id", "teachers"."age" AS "teachers.age", "teachers"."name" AS
"teachers.name", "teachers"."created_at" AS "teachers.created_at",
"teachers"."updated_at" AS "teachers.updated_at",
"teachers.student_teacher"."id" AS "teachers.student_teacher.id",
"teachers.student_teacher"."teacher_id" AS
"teachers.student_teacher.teacher_id", "teachers.student_teacher"."student_id"
AS "teachers.student_teacher.student_id"
FROM "student" AS "student"
INNER JOIN (
    "student_teacher" AS "teachers.student_teacher"
    INNER JOIN "teacher" AS "teachers"
    ON "teachers"."id" = "teachers.student_teacher"."teacher_id"
)
ON "student"."id"  = "teachers.student_teacher"."student_id"
AND "teachers"."id" IN (3, 2)
ORDER BY "student"."id" DESC OFFSET 6;

“Test 2”: Bug - Wrong query generated… but this case returns expected result by “coincidence”

    Student.findAndCount({
        limit: 5,
        offset: 6,
        order: [["id", "DESC"]],
        include: [
            {
                model: Teacher,
                as: 'teachers',
                where: {
                    id: {$in: [3, 2]}
                }
            }
        ]
    });
SELECT "student".*, "teachers"."id" AS "teachers.id", "teachers"."age" AS
"teachers.age", "teachers"."name" AS "teachers.name", "teachers"."created_at"
AS "teachers.created_at", "teachers"."updated_at" AS "teachers.updated_at",
"teachers.student_teacher"."id" AS "teachers.student_teacher.id",
"teachers.student_teacher"."teacher_id" AS
"teachers.student_teacher.teacher_id", "teachers.student_teacher"."student_id"
AS "teachers.student_teacher.student_id"
FROM (
    SELECT "student"."id", "student"."age", "student"."name",
    "student"."created_at", "student"."updated_at"
    FROM "student" AS "student"
    WHERE (
        SELECT "student_teacher"."id"
        FROM "student_teacher" AS "student_teacher"
        INNER JOIN "teacher" AS "teacher"
        ON "student_teacher"."teacher_id" = "teacher"."id"
        WHERE ("student"."id" = "student_teacher"."student_id")
        LIMIT 1
    ) IS NOT NULL
    ORDER BY "student"."id" DESC LIMIT 5 OFFSET 6
) AS "student"
INNER JOIN (
    "student_teacher" AS "teachers.student_teacher"
    INNER JOIN "teacher" AS "teachers"
    ON "teachers"."id" = "teachers.student_teacher"."teacher_id"
)
ON "student"."id" = "teachers.student_teacher"."student_id"
AND "teachers"."id" IN (3, 2)
ORDER BY "student"."id" DESC;

“Test 3”: Bug - Wrong query - returns unexpected results

    Student.findAndCount({
        limit: 5,
        offset: 6,
        include: [
            {
                model: Teacher,
                as: 'teachers',
                where: {
                    id: {$in: [3, 2]}
                }
            }
        ]
    });
SELECT "student".*, "teachers"."id" AS "teachers.id", "teachers"."age" AS
"teachers.age", "teachers"."name" AS "teachers.name", "teachers"."created_at"
AS "teachers.created_at", "teachers"."updated_at" AS "teachers.updated_at",
"teachers.student_teacher"."id" AS "teachers.student_teacher.id",
"teachers.student_teacher"."teacher_id" AS
"teachers.student_teacher.teacher_id", "teachers.student_teacher"."student_id"
AS "teachers.student_teacher.student_id"
FROM (
    SELECT "student"."id", "student"."age", "student"."name",
    "student"."created_at", "student"."updated_at"
    FROM "student" AS "student"
    WHERE (
        SELECT "student_teacher"."id"
        FROM "student_teacher" AS "student_teacher"
        INNER JOIN "teacher" AS "teacher"
        ON "student_teacher"."teacher_id" = "teacher"."id"
        WHERE ("student"."id" = "student_teacher"."student_id")
        LIMIT 1
    ) IS NOT NULL LIMIT 5 OFFSET 6
) AS "student"
INNER JOIN (
    "student_teacher" AS "teachers.student_teacher"
    INNER JOIN "teacher" AS "teachers"
    ON "teachers"."id" = "teachers.student_teacher"."teacher_id"
)
ON "student"."id" = "teachers.student_teacher"."student_id"
AND "teachers"."id" IN (3, 2);

As I look at queries it seems it would be great if generated queries for test cases 2 and 3 would be the same as in 1 with LIMIT included at the end of query, wouldn’t it?

Thank you for your work!

Issue Analytics

  • State:closed
  • Created 8 years ago
  • Reactions:2
  • Comments:23 (13 by maintainers)

github_iconTop GitHub Comments

13reactions
ybrodskycommented, Aug 3, 2016

@janmeier my case is exactly the same as @fogine first post.

I have noticed that adding the option subQuery: false seems to produce the desired mysql query. Is there any downside of using this?

1reaction
ybrodskycommented, Aug 3, 2016

Same issue here. Any progress or workaround?

Is there any reason for those subqueries being there?

Read more comments on GitHub >

github_iconTop Results From Across the Web

SELECT LIMIT 1 query returns unexpected results when the ...
My question is: Why does this happen? There is no WHERE clause in the query so there should be no reason for MySQL...
Read more >
SELECT query with LIMIT clause returns non-deterministic ...
This article explains why SELECT query with LIMIT clause returns non-deterministic result although ORDER BY exists in a different level like ...
Read more >
Difference between WHERE and ON in SQL - Data School
Filtering data. Both the ON and WHERE clause can be used to filter data in a query. There are readability and accuracy concerns...
Read more >
Advanced SQL
INNER JOIN clause is an alternative to WHERE clause, and is used to match primary and foreign keys. An INNER join will only...
Read more >
SELECT
limit -clause ::= [ LIMIT [offset,] row_count | row_count OFFSET offset | ALL ... When the topmost SELECT query finishes, all resources associated...
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