This website is a work in progress.

Immutable pagination

Immutable pagination

When you will start having a lot of content, you might want to add pagination. From a developer perspective, it is very straight forward to enable pagination on a query. Let's continue with our list of posts by adding more parameters

const HomeContainer = withPhenomicApi(Home, () => ({
  posts: query({ path: "content/posts", limit: 2 })
}));

Here we just added a limit parameter. That's enough to limit the number of items, but won't help to handle next pages.

We decided to solve the pagination problem with a single parameter: after. This parameter is a hash that is pointing to specific place in the list for the given path.

Before adding it in the query, we need to actually create a link to access the next page! Let's add a link in our Home, after our list of posts

<div>
  {posts.node &&
    posts.node.next && (
      <Link to={`/after/${posts.node.next}/`}>Older posts</Link>
    )}
</div>

This link will look like http://localhost:3333/after/MjAxNC0wNS0yMC1zdWR3ZWItMjAxNA==

We now have to be able to read it from the router so that we can pass it to the query. So, we will add a route in the router:

export default createApp(() => (
  <Router history={browserHistory}>
    <Route path="/" component={HomeContainer} />
    <Route path="/after/:after" component={HomeContainer} />
    <Route path="/blog/*" component={BlogPostContainer} />
  </Router>
));

One more thing is to be done now that we have the url understood by the router: we need to use after in our query. Let's modify the query like this:

const HomeContainer = withPhenomicApi(Home, props => ({
  posts: query({ path: "content/posts", limit: 2, after: props.params.after })
}));

With this we should now have the url working. And now you have a pagination that will never die. It's like an immutable pagination!

What does this mean? Think about the url /page/2. You may want to share it... but content may have changed if new posts were added, right? With our approach, using a hash, we have a url that never changes and that will always return the same result with the same query. This process involves generating all possible pages under the hood, but that's Phenomic's job.

Oh, and before continuing, you should add another simple link for "Newer posts"

<div>
  {posts.node &&
    posts.node.previous && (
      <Link
        to={
          posts.node.previousPageIsFirst
            ? `/`
            : `/after/${posts.node.previous}/`
        }
      >
        Newer posts
      </Link>
    )}
</div>

Continue tutorial