This post is also published on:
Progressive Web App (PWA) is a promising technology, which allows web apps to take on a more native role. However, since the technology is still in its infancy, there's still uncertainty on where to start with PWAs.
About a month ago, Yohan Totting posted the #WWWIDChallenge on Progressive Web Apps (PWA). The challenge was to create a feed reader for the WWWID Medium publication as a PWA. I was free to choose any framework I wanted, and decided to go the JAMstack route and create it as a statically-generated PWA.
So, essentially:
- A statically-generated PWA built with GatsbyJS, hosted on Netlify.
- A cron job runs the Netlify webhook to re-build pages once a day
- HTTP/2 (provided by default on Netlify) with server push
- Uses
gatsby-image
to enable image optimisation with Sharp + lazy-loading
Attempt #1
Let's start with a basic setup. A Gatsby.js with minimal styles, and a basic service worker setup using gatsby-plugin-offline
. We're going to see if Gatsby's "performance by default" mantra really takes hold. And yep, it is.
#WWWIDChallenge Attempt #1. JAMstack, statically-generated with @gatsbyjs. pic.twitter.com/FWJhD09agR
— 🎺KUINGIN KAU MENJADI ISTRIKU🎺 (@resir014) February 14, 2018
Attempt #2
Since this website is statically generated, we're gonna have to find a way to dynamically generate the static pages. So I decided to move my hosting to Netlify, which supports HTTP/2 as well as webhooks which can be used trigger Gatsby’s build command. I have a cron job running on a VPS to run said webhook to build our Gatsby site. Unfortunately, the PWA score goes down a bit, since by default, Netlify doesn't automatically redirect to HTTPS, but at least it's some progress.
#WWWIDChallenge Attempt #2. Finally moving to Netlify for that sweet HTTP/2. Will look into image processing with Sharp tomorrow. pic.twitter.com/w5MxdRN0ry
— 🎺KUINGIN KAU MENJADI ISTRIKU🎺 (@resir014) February 14, 2018
Attempt #3
Now we're gonna take it up a notch. We'll use all the best practices laid out by Gatsby, which means, image processing + lazyloading. Gatsby uses Sharp to process these images, resize them to fit the container's maximum width, and runs optimisation tasks.
During this attempt, I then realised that I've been running the wrong WebPageTest test. I should've ran the Slow 3G quick test + Lighthouse. So I did just that, and the results are still promising.
#WWWIDChallenge Attempt #3, added image processing with Sharp + lazyloading with `gatsby-image`. Bisa diakses di https://t.co/9VdCebOqWa pic.twitter.com/u7T6yqCdVA
— 🎺KUINGIN KAU MENJADI ISTRIKU🎺 (@resir014) February 15, 2018
The Result
As a result, I managed to load a statically-generated, service-worker-enabled website to load in less than 5 seconds, thanks to Gatsby. The website remains statically-generated, to stick true to the JAMstack principles, but remains dynamic by having the content rebuilt daily. With a close-to-default service-worker-enabled GatsbyJS setup, it's possible to make a website load in less than 5 seconds on a slow 3G connection.
To view the final result of the project, click here. To view the source code, click here.