mirror of
https://github.com/hasura/graphql-engine.git
synced 2024-12-18 04:51:35 +03:00
614c0dab80
Blocked on https://github.com/hasura/graphql-engine-mono/pull/1640. While fiddling with BigQuery I noticed a severe issue with offset/limit for array-aggregates. I've fixed it now. The basic problem was that I was using a query like this: ```graphql query MyQuery { hasura_Artist(order_by: {artist_self_id: asc}) { artist_self_id albums_aggregate(order_by: {album_self_id: asc}, limit: 2) { nodes { album_self_id } aggregate { count } } } } ``` Producing this SQL: ```sql SELECT `t_Artist1`.`artist_self_id` AS `artist_self_id`, STRUCT(IFNULL(`aa_albums1`.`nodes`, NULL) AS `nodes`, IFNULL(`aa_albums1`.`aggregate`, STRUCT(0 AS `count`)) AS `aggregate`) AS `albums_aggregate` FROM `hasura`.`Artist` AS `t_Artist1` LEFT OUTER JOIN (SELECT ARRAY_AGG(STRUCT(`t_Album1`.`album_self_id` AS `album_self_id`) ORDER BY (`t_Album1`.`album_self_id`) ASC) AS `nodes`, STRUCT(COUNT(*) AS `count`) AS `aggregate`, `t_Album1`.`artist_other_id` AS `artist_other_id` FROM (SELECT * FROM `hasura`.`Album` AS `t_Album1` ORDER BY (`t_Album1`.`album_self_id`) ASC NULLS FIRST -- PROBLEM HERE LIMIT @param0) AS `t_Album1` GROUP BY `t_Album1`.`artist_other_id`) AS `aa_albums1` ON (`aa_albums1`.`artist_other_id` = `t_Artist1`.`artist_self_id`) ORDER BY (`t_Artist1`.`artist_self_id`) ASC NULLS FIRST ``` Note the `LIMIT @param0` -- that is incorrect because we want to limit per artist. Instead, we want: ```sql SELECT `t_Artist1`.`artist_self_id` AS `artist_self_id`, STRUCT(IFNULL(`aa_albums1`.`nodes`, NULL) AS `nodes`, IFNULL(`aa_albums1`.`aggregate`, STRUCT(0 AS `count`)) AS `aggregate`) AS `albums_aggregate` FROM `hasura`.`Artist` AS `t_Artist1` LEFT OUTER JOIN (SELECT ARRAY_AGG(STRUCT(`t_Album1`.`album_self_id` AS `album_self_id`) ORDER BY (`t_Album1`.`album_self_id`) ASC) AS `nodes`, STRUCT(COUNT(*) AS `count`) AS `aggregate`, `t_Album1`.`artist_other_id` AS `artist_other_id` FROM (SELECT *, -- ADDED ROW_NUMBER() OVER(PARTITION BY artist_other_id) artist_album_index FROM `hasura`.`Album` AS `t_Album1` ORDER BY (`t_Album1`.`album_self_id`) ASC NULLS FIRST ) AS `t_Album1` -- CHANGED WHERE artist_album_index <= @param GROUP BY `t_Album1`.`artist_other_id`) AS `aa_albums1` ON (`aa_albums1`.`artist_other_id` = `t_Artist1`.`artist_self_id`) ORDER BY (`t_Artist1`.`artist_self_id`) ASC NULLS FIRST ``` That serves both the LIMIT/OFFSET function in the where clause. Then, both the ARRAY_AGG and the COUNT are correct per artist. I've updated my Haskell test suite to add regression tests for this. I'll push a commit for Python tests shortly. The tests still pass there. This just fixes a case that we hadn't noticed. https://github.com/hasura/graphql-engine-mono/pull/1641 GitOrigin-RevId: 49933fa5e09a9306c89565743ecccf2cb54eaa80
190 lines
4.4 KiB
YAML
190 lines
4.4 KiB
YAML
- description: Aggregate with a limit using nodes, count
|
|
url: /v1/graphql
|
|
status: 200
|
|
response:
|
|
data:
|
|
hasura_Artist:
|
|
- artist_self_id: '1000'
|
|
albums_aggregate:
|
|
nodes:
|
|
- album_self_id: '2002'
|
|
aggregate:
|
|
count: '1'
|
|
- artist_self_id: '1001'
|
|
albums_aggregate:
|
|
nodes:
|
|
- album_self_id: '2000'
|
|
aggregate:
|
|
count: '1'
|
|
- artist_self_id: '1002'
|
|
albums_aggregate:
|
|
nodes:
|
|
- album_self_id: '2003'
|
|
aggregate:
|
|
count: '1'
|
|
query:
|
|
query: |
|
|
query MyQuery {
|
|
hasura_Artist(order_by: {artist_self_id: asc}) {
|
|
artist_self_id
|
|
albums_aggregate(order_by: {album_self_id: asc}, limit: 1) {
|
|
nodes {
|
|
album_self_id
|
|
}
|
|
aggregate {
|
|
count
|
|
}
|
|
}
|
|
}
|
|
}
|
|
|
|
- description: Aggregate with order by using nodes, count, sum
|
|
url: /v1/graphql
|
|
status: 200
|
|
response:
|
|
data:
|
|
hasura_Artist:
|
|
- artist_self_id: '1001'
|
|
albums_aggregate:
|
|
nodes:
|
|
- album_self_id: '2000'
|
|
- album_self_id: '2001'
|
|
aggregate:
|
|
count: '2'
|
|
sum:
|
|
album_self_id: '4001'
|
|
- artist_self_id: '1002'
|
|
albums_aggregate:
|
|
nodes:
|
|
- album_self_id: '2003'
|
|
- album_self_id: '2004'
|
|
aggregate:
|
|
count: '2'
|
|
sum:
|
|
album_self_id: '4007'
|
|
- artist_self_id: '1000'
|
|
albums_aggregate:
|
|
nodes:
|
|
- album_self_id: '2002'
|
|
- album_self_id: '2005'
|
|
aggregate:
|
|
count: '2'
|
|
sum:
|
|
album_self_id: '4007'
|
|
query:
|
|
query: |
|
|
query MyQuery {
|
|
hasura_Artist {
|
|
artist_self_id
|
|
albums_aggregate(order_by: {album_self_id: asc}) {
|
|
nodes {
|
|
album_self_id
|
|
}
|
|
aggregate {
|
|
count
|
|
sum {
|
|
album_self_id
|
|
}
|
|
}
|
|
}
|
|
}
|
|
}
|
|
|
|
- description: Aggregate with limit using sum, nodes
|
|
url: /v1/graphql
|
|
status: 200
|
|
response:
|
|
data:
|
|
hasura_Artist:
|
|
- artist_self_id: '1001'
|
|
albums_aggregate:
|
|
nodes:
|
|
- album_self_id: '2000'
|
|
aggregate:
|
|
count: '1'
|
|
sum:
|
|
album_self_id: '2000'
|
|
- artist_self_id: '1002'
|
|
albums_aggregate:
|
|
nodes:
|
|
- album_self_id: '2003'
|
|
aggregate:
|
|
count: '1'
|
|
sum:
|
|
album_self_id: '2003'
|
|
- artist_self_id: '1000'
|
|
albums_aggregate:
|
|
nodes:
|
|
- album_self_id: '2002'
|
|
aggregate:
|
|
count: '1'
|
|
sum:
|
|
album_self_id: '2002'
|
|
query:
|
|
query: |
|
|
query MyQuery {
|
|
hasura_Artist {
|
|
artist_self_id
|
|
albums_aggregate(order_by: {album_self_id: asc}, limit: 1) {
|
|
nodes {
|
|
album_self_id
|
|
}
|
|
aggregate {
|
|
count
|
|
sum {
|
|
album_self_id
|
|
}
|
|
}
|
|
}
|
|
}
|
|
}
|
|
|
|
- description: Aggregate with offset using sum, nodes
|
|
url: /v1/graphql
|
|
status: 200
|
|
response:
|
|
data:
|
|
hasura_Artist:
|
|
- artist_self_id: '1001'
|
|
albums_aggregate:
|
|
nodes:
|
|
- album_self_id: '2001'
|
|
aggregate:
|
|
count: '1'
|
|
sum:
|
|
album_self_id: '2001'
|
|
- artist_self_id: '1002'
|
|
albums_aggregate:
|
|
nodes:
|
|
- album_self_id: '2004'
|
|
aggregate:
|
|
count: '1'
|
|
sum:
|
|
album_self_id: '2004'
|
|
- artist_self_id: '1000'
|
|
albums_aggregate:
|
|
nodes:
|
|
- album_self_id: '2005'
|
|
aggregate:
|
|
count: '1'
|
|
sum:
|
|
album_self_id: '2005'
|
|
query:
|
|
query: |
|
|
query MyQuery {
|
|
hasura_Artist {
|
|
artist_self_id
|
|
albums_aggregate(order_by: {album_self_id: asc}, offset: 1) {
|
|
nodes {
|
|
album_self_id
|
|
}
|
|
aggregate {
|
|
count
|
|
sum {
|
|
album_self_id
|
|
}
|
|
}
|
|
}
|
|
}
|
|
}
|