GraphQL API pagination implementation

How pagination has been implemented in our GraphQL API

Arnaud Bezançon
WorkflowGen
3 min readFeb 14, 2017

--

Pagination is a basic feature for browsing lists returned by an API and definitely plays an important role in the overall developer experience. With its flexible nature, GraphQL lets you decide how to implement pagination according to your requirements.

This freedom to choose can also mean a decision-making nightmare!

There are actually many possible solutions as described in this great post, with each solution having its advantages and drawbacks.

Relay pagination

Relay cursor connections pagination is perhaps the most powerful implementation and is a natural choice when using Relay in the front-end.

But it also introduces new concepts as “Connections”, “Edges” and “Nodes”, which can add some friction to the learning curves of developers who use the API and the ones who implement it!

Still, these efforts can be justified by the level of features Relay cursor connections pagination provides, especially when developers use React with Relay.

The relative complexity of this solution was not a reason to choose another one instead, however.

Sometimes you have to decide between perfection and efficiency.

Our objective was to deliver the WorkflowGen GraphQL API in three months — the kind of deadline that really helps to find a way out of the labyrinth of the decision-making process!

Due to our huge existing code base and SQL queries that use a classic page number pagination, we had to skip Relay cursor connections.

We tried to see how far we could go with Relay cursor connections by reusing our existing code, but such an implementation would either have been partial (with no backward navigation) or entail too much effort in rewriting certain SQL queries to support user-defined sort orders compatible with bidirectional cursor-based navigation.

Page number pagination

Our current GraphQL pagination implementation is a classic page number based pagination that has the advantage of being available now for all lists, not to mention straightforward.

Pagination with order by and filter settings

We have reused some of Relay’s PageInfo type attributes: totalCount, hasNextPage and hasPreviousPage.

The corresponding “requests” field definition:

The Page input type:

RequestListPage GraphQL type:

To retrieve the total count without the list of items, you just need to set the page number to 0:

Conclusion

A GraphQL schema can be extended with limited impacts and breaking changes for developers. A page number pagination is simple and intuitive, but doesn’t have some advanced features provided by a cursor-type pagination, so we’re keeping in mind the possibility of delivering Relay cursor connections for some types in future releases.

We also expect a lot of feedback from our customers, and we’ll rely on the “organic” nature of the GraphQL schema to improve our implementation with incremental cycles.

The dawn of GraphQL dialects

GraphQL opens limitless design possibilities, and perhaps in the future, some part of the schema will be standardized (such as a pagination viewer with Relay or schema.org for JSON). This should accelerate API implementation and interoperability, which in turn will free up more time for developers to work on other levels of features.

--

--

Arnaud Bezançon
WorkflowGen

Full Stack Architect, Creator of WorkflowGen, Advantys co-founder and CTO.