GraphQL cursors for keyset pagination not working as expected when objects' timestamps contain millisecond data
When paginating a GraphQL type that uses pagination - for example Issues.
- If more than one has the same timestamp AND
- This timestamp has a ms component that's not
0000
(almost always will happen for generated fields likecreated_at
) AND - You ask for a page that ends between two of these objects
then the second page will not contain the objects that share the same timestamp.
This occurs because when we serialize the date into our GraphQL cursors we use to_s
, which drops the millisecond value. We then ask the DB to look for:
("issues"."created_at" < '2020-06-10 21:20:55')
OR (
"issues"."created_at" = '2020-06-10 21:20:55'
AND
"issues"."id" < 8
)
OR ("issues"."created_at" IS NULL)
) AND "issues"."id" != 8
Because we don't pass a millisecond value, the DB assumes we want 0000
, so it does not return any object that has a MS value that's not 0000
.
Edited by Mario de la Ossa