Marketplace
Guides
Pagination

Pagination

The API provides pagination for data sets that can become quite large. All pagination is implemented using the GraphQL Cursor Connections Specification (opens in a new tab). With this pattern, you use cursors to traverse through a data set (so-called “Connections”). Each cursor represents a specific position in the data set. The limited number of returned nodes together is called a page. You use metadata (pageInfo) about the current page to determine where previous and next pages are. You can recognize a paginated field by the name: if it ends in Connection, you have to use pagination to retrieve data.


The default number of nodes on a page is 20, while the maximum number of nodes is 100.

How it works

To demonstrate pagination, we use the viewer query: it has a connection to companies.

query Viewer {
    viewer {
        ... on User {
            id
            companies {
                pageInfo {
                    startCursor
                    endCursor
                    hasNextPage
                    hasPreviousPage
                }
                edges {
                    node {
                        id
                        name
                    }
                }
            }
        }
    }
}

Inside the connection companies, we can query for pageInfo, which contains metadata about pagination:

  • startCursor contains the cursor of the first item on the page.
  • endCursor contains the cursor of the last item on the page.
  • hasNextPage is a boolean indicating whether there is a next page.
  • hasPreviousPage is a boolean indicating whether there is a previous page.

When executing this query, you will receive the first page, which looks something like this:

{
    "data": {
        "viewer": {
            "id": "1",
            "companies": {
                "pageInfo": {
                    "startCursor": "R1BDOk46Ng==",
                    "endCursor": "R1BDOk46MjY=",
                    "hasNextPage": true,
                    "hasPreviousPage": false
                },
                "edges": [
                    {
                        "cursor": "R1BDOk46Ng==",
                        "node": {
                            "id": "1",
                            "name": "Beequip B.V."
                        }
                    }
                    // More data
                ]
            }
        }
    }
}

With this data, you can build follow-up requests for next or previous pages.

Forward navigation

All connections provide an after argument to let you retrieve next pages. It determines the element after which you want to return nodes.

Using the previous example, hasNextPage is true so there is at least one more page, and pageInfo has an endCursor of R1BDOk46MjY=. To retrieve the next page, supply that cursor to after:

query Viewer {
    viewer {
        ... on User {
            id
            companies(after: "R1BDOk46MjY=") {
                pageInfo {
                    startCursor
                    endCursor
                    hasNextPage
                    hasPreviousPage
                }
                edges {
                    node {
                        id
                        name
                    }
                }
            }
        }
    }
}

This will yield a result like this:

{
    "data": {
        "viewer": {
            "id": "1",
            "companies": {
                "pageInfo": {
                    "startCursor": "R1BDOk46Nw==",
                    "endCursor": "R1BDOk46MTA=",
                    "hasNextPage": false,
                    "hasPreviousPage": true
                },
                "edges": [
                    {
                        "cursor": "R1BDOk46Nw==",
                        "node": {
                            "id": "2",
                            "name": "Vandelay Industries"
                        }
                    }
                    // More data
                ]
            }
        }
    }
}

Backward navigation

Backward navigation is similar to forward navigation, only using the before argument. It determines the element before which you want to return nodes.

query Viewer {
    viewer {
        ... on User {
            id
            companies(before: "R1BDOk46Nw==") {
                pageInfo {
                    startCursor
                    endCursor
                    hasNextPage
                    hasPreviousPage
                }
                edges {
                    node {
                        id
                        name
                    }
                }
            }
        }
    }
}
{
    "data": {
        "viewer": {
            "id": "1",
            "companies": {
                "pageInfo": {
                    "startCursor": "R1BDOk46Ng==",
                    "endCursor": "R1BDOk46MjY=",
                    "hasNextPage": true,
                    "hasPreviousPage": false
                },
                "edges": [
                    {
                        "cursor": "R1BDOk46Ng==",
                        "node": {
                            "id": "1",
                            "name": "Beequip B.V."
                        }
                    }
                    // More data
                ]
            }
        }
    }
}

Changing the number of items

Use the first or last arguments to change the number of nodes on a page.

Combine first with after when navigating forward:

query Viewer {
    viewer {
        ... on User {
            id
            companies(first: 100, after: "R1BDOk46Ng==") {
                pageInfo {
                    startCursor
                    endCursor
                    hasNextPage
                    hasPreviousPage
                }
                edges {
                    node {
                        id
                        name
                    }
                }
            }
        }
    }
}

Combine last with before when navigating backward:

query Viewer {
    viewer {
        ... on User {
            id
            companies(last: 100, before: "R1BDOk46Ng==") {
                pageInfo {
                    startCursor
                    endCursor
                    hasNextPage
                    hasPreviousPage
                }
                edges {
                    node {
                        id
                        name
                    }
                }
            }
        }
    }
}

Total number of items

Each connection has a totalCount field that returns the total number of nodes in the data set.

query Viewer {
    viewer {
        ... on User {
            id
            companies {
                totalCount
                pageInfo {
                    startCursor
                    endCursor
                    hasNextPage
                    hasPreviousPage
                }
                edges {
                    node {
                        id
                        name
                    }
                }
            }
        }
    }
}