Published on

Understanding the lifecycle of Gatsby’s time-based Browser APIs

Authors

If you haven’t heard lately, GatsbyJS has picked up a ton of steam. We recently, at work, migrated from a React on Rails project, to a ReactJS/S3 project to a GatsbyJS project. If you’re interested in some of the effects and the why you can check out this post here.

The point of this post isn’t to elaborate on GatsbyJS as a core framework, if you’re interested in learning more about them, I’d suggest starting at their docs here. The tldr; is that GatsbyJS is a SSR React project that renders html/css. The main use case is for SEO ability (imo). Today I’m going to dive a little further into some of their more prevalent Browser APIs and when things get called and use cases for such. Let’s dive right in!

onClientEntry

gatsby-browser.js
// This is our gatsby-browser.js file. I'll add to it periodically. // Don't worry I'll link the repo at the end for you to play with :)exports.onClientEntry = () => {
  console.log("onClientEntry")
}

From their docs this is called when the Gatsby browser runtime first starts and an example above. We use this for Analytics data, creating our Redux Store and other small things. This will get run for every “session” of the site, meaning if you open a new tab it WILL fire again.

onInitialClientRender

gatsby-browser.js
exports.onInitialClientRender = () => {
  console.log("onInitialClientRender")
}

This gets called when the initial render of Gatsby App is done on the client. So we can see here the order is onClientEntry then onInitialClientRender. We don’t use this for anything

onPostPrefetchPathname

gatsby-browser.js
exports.onPostPrefetchPathname = () => {
  console.log("onPostPrefetchPathname")
}

This gets called when prefetching for a pathname is successful. Specifically this allows for plugins with custom prefetching logic. This only gets called once per session on the website as far as I can tell. You can see this get called twice once two routes are present.

onPreRouteUpdate

gatsby-browser.js
exports.onPreRouteUpdate = () => {
  console.log("onPreRouteUpdate")
}

This gets called when changing location is started. This is used for updating things that are dependent on the location changing. For example intercom won’t recognize javascript changes to the window object (at least at the time of writing this) so we update intercom that the page is changing. You can see it’s called after the actual render of the second page.

onPrefetchPathname

gatsby-browser.js
exports.onPrefetchPathname = () => {
  console.log("onPrefetchPathname")
}

This gets called when prefetching for a pathname is triggered. Similar to onPostPrefetchPathname this is used for plugins with custom prefetching logic.

onRouteUpdate

gatsby-browser.js
exports.onRouteUpdate = () => {
  console.log("onRouteUpdate")
}

This gets called when the user changes routes. This gets called right after onPreRouteUpdate (who would’ve guessed). A good use case for this is if you need update Google Analytics on the location changing.

onRouteUpdateDelayed

gatsby-browser.js
exports.onRouteUpdateDelayed = () => {
  console.log("onRouteUpdateDelayed")
}

This gets called when the user changes routes and it is longer than 1 second. We have a blazing fast website (thanks to Gatsby) but I assume this would be to render an HoC to render a spinner or something of the sort. I don’t have a render for this guy, but

And that’s it. Feel free to comment any suggestions or edits as they evolve. This is current (as of November 12th, 2019) but they seem to rapidly iterate so some of these will change over time. Should you have any questions feel free to comment and I’m pretty good about responding. You can copy the following into your gatsby-browser.js file (if you don’t have one put it at the root of your Gatsby project).

gatsby-browser.js
exports.onClientEntry = () => {
  console.log("onClientEntry")
}

exports.onInitialClientRender = () => {
  console.log("onInitialClientRender")
}

exports.onPostPrefetchPathname = () => {
  console.log("onPostPrefetchPathname")
}

exports.onPreRouteUpdate = () => {
  console.log("onPreRouteUpdate")
}

exports.onPrefetchPathname = () => {
  console.log("onPrefetchPathname")
}

exports.onRouteUpdate = () => {
  console.log("onRouteUpdate")
}

exports.onRouteUpdateDelayed = () => {
  console.log("onRouteUpdateDelayed")
}