Reputation: 30995
we have to rebuild a backend app based on REST services and since we have a lot of nested levels in the services we decided to innovate and try GraphQL.
We started doing simple things and the project looks very promising, however we started facing real world problems like pagination. In REST, pagination approach was straightforward, we use GET method with some parameters like pageSize
and pageNumber
(or offset
) and we build sql queries to perform this pagination.
In GraphQL we were tackling the problem following the same approach, for example having this query:
users(size:5 offset:2) {
id
name
}
This approach looked simple to implement, however after digging deeper we found that the "best" pattern to implement this is the Connection one, which the query would look like this:
users(first:2) {
totalCount
edges {
node {
name
}
cursor
}
pageInfo {
endCursor
hasNextPage
}
}
Our data is persisted in a relational database, therefore I don't see how cursors can help (unless perhaps if I use autoincrement ID?).
Why is this complex approach the recommended one over the simple one? And also what cursor and endCursor will be storing? Am I misunderstanding something in my learning path?
Upvotes: 4
Views: 2658
Reputation: 15429
The Connection
spec was originally created for Relay (Facebook's GraphQL client). It later developed a life of its own, and is now considered a best practice, regardless of the client. But (and that's a huge but), it most definitely does not map well to every use-case.
If you see value in implementing the Connection
pagination style, you have 2 options:
1) Treat after
as the offset (meaning a number would be passed), and first
as the limit:
SELECT * FROM ORDER BY timestamp OFFSET $after LIMIT $first
The same for before
and last
, just different direction.
2) Another way is to treat after
/before
as the last seen value of the sort column (so an actual (obfuscated) value would be passed):
SELECT * FROM ORDER BY timestamp WHERE timestamp > $after LIMIT $first
That said, if you don't benefit from the Connection
approach, feel free to ignore it. Especially if you're not even using Relay as the client. It's a completely optional thing and should not be shoehorned where it doesn't belong.
Upvotes: 5