Power-Up Your React or Angular App with Progressive Web App (PWA) Capabilities in Under 10 Minutes

Giving your users a fast, reliable and engaging user experience is the future. Fearing Google Lighthouse is the past.

Lewis Fairweather
Nov 20, 2019 · 7 min read

Giving your app progressive powers

Answer: everyone wants it

PWA’s have become a low-cost alternative to native applications. The array of benefits are enticing. The PWA bypasses the need for distribution through a centralised application store which has its limitations in terms of discoverability. It prevents the need for multiple teams with different skillsets, whilst limiting compatibility issues in code. Furthermore, the one-click install process ensures that your users have a much higher likelihood of having your web app installed on their device.

They visit your site ONCE then…

It’s as easy as that.

Where the magic happens


Don’t lose your users attention

Note: I will reference javascript (.js) files throughout, however if you use TypeScript then .js & .ts can be assumed interchangeable. You can write completely valid typescript using only javascript, therefore use either .js or .ts when creating the new files.

— — — — 1

Where to start — Create or Integrate


npm i -g @angular/cli && ng new new-app
// creates 'new-app'


ng add @angular/pwa --project *project-name*
// Adds the @angular/service-worker package to your project.

— — — — — — — — — — — — — — — — — — — — — — — — — — — — — —


npm i create-react-app -g && create-react-app new-app
// creates the app 'new-app'

Make sure that the manifest.json file is linked in /public/index.html

<link rel=”manifest” href=”%PUBLIC_URL%/manifest.json” />
// replace %PUBLIC_URL% with production directory

The service worker file serviceWorker.js is then created whenever you npm run build to build your production app.

— — — — — — — — — 2

The Manifest File

short_name: the name taken when added to the home screen and situated amongst your other apps

name: the name shown in the ‘add to home screen prompt’. short_name is used if not set.

icons: your app icons (logo) in varying sizes for maximum compatibility with different sized devices.

Recommendation: include a 192x192 pixel icon and a 512x512 pixel icon as they can be scaled automatically to size.

start_url: initial navigation path. The location in your app that you would like your users to start when they open it.

display: used to customize the browser view display for different app experiences. standalone will give it the native feel.

Options: standalone, fullscreen, minimal-ui & browser

theme_color: browser toolbar color

background_color: splash screen color when app is starting up.

Recommendation: the theme_color should match the meta theme color specified in your document head


"orientation": "landscape" // for games
"scope": "/maps/" // directory considered as part of your app

— — — — — — — — — — — — — 3

The Service Worker File


First you need to install workbox as a dev dependency.

npm install workbox-build --save-dev
  1. Add workbox.precaching.precacheAndRoute([]); to your serviceWorker.js file.
  2. Createsrc/sw-build.js (the file that builds the service worker) & src/sw.js (the source service worker file)
  3. Add the code below to sw-build.js .

In serviceWorker.js, change const swUrl = ${process.env.PUBLIC_URL}/service-worker.js to const swUrl = ${process.env.PUBLIC_URL}/sw.js; (the sw.js file that is built for production)


In the ngsw-config file you define:

  • Index — The file that serves as the index page. Usually /index.html .
  • App Data — Describes a particular version of the app. Used in SwUpdate service includes data in the update notifications.
  • Asset Groups — Your apps assets that are updated along with the app (versioned). URL patterns can match host URLs or external URLs (CDN’s)
  • Data Groups — Cached according to manually configured policies. API requests and data dependencies are handled here. (not-versioned)
  • Navigation URLs — (Optional) list of URLs that will redirect to the index file.

— — — — — — — — — — — — — — — 4

Register, Optimize and Serve Your Service Worker


IF you are not using CRA to build your React app then you can use workbox-webpack-plugin as the build step required to register your Service Worker.

Run npm install --save-dev workbox-webpack-plugin

if ("serviceWorker" in navigator){    window.addEventListener("load", () => {

Open the webpack.config.js file and configure the workbox plugin.

const WorkboxWebpackPlugin = require("workbox-webpack-plugin");

plugins: [ // add this as a plugin:

, new WorkboxWebpackPlugin.InjectManifest({
swSrc: "./src/webpack-sw.js",
swDest: "sw.js"

Then create the webpack-sw.js file and write

// self.__precacheManifest is a variable that is imported from a
// dynamically created file (via workbox)

Now when you npm run build sw.js will be generated along with your built app files.

Handling & Caching Dynamic Data

/https:\/\/api\.yourapi\.com\/data/, // replace with your API URL
new workbox.strategies.NetworkFirst({
cacheName: "api_data", // call this what you want
plugins: [
new workbox.expiration.Plugin({
maxAgeSeconds: 10 * 60 // 10 minutes



You’ll then want to programmatically check for updates on behalf of the user. Notifying them if a new version of the app is available. This will then attempt to update the cache with the new files/assets/data. This can be done effectively with an Angular Service which we will create as sw-update.service.ts .

This is an example SWUpdateService class using an Angular Material SnackBar to notify the users of updates.

— — — — — — — — — — — — — — — — — — Done ✓

Any issues, make sure that you fill the PWA requirements on this checklist to ensure you are fully PWA ready.

Any questions, feel free to ask in the comments!

Anything I’ve missed, help me to become a better human by leaving me a note.

Some helpful resources

The Startup

Get smarter at building your thing. Join The Startup’s +788K followers.

Sign up for Top 10 Stories

By The Startup

Get smarter at building your thing. Subscribe to receive The Startup's top 10 most read stories — delivered straight into your inbox, once a week. Take a look.

By signing up, you will create a Medium account if you don’t already have one. Review our Privacy Policy for more information about our privacy practices.

Check your inbox
Medium sent you an email at to complete your subscription.

Lewis Fairweather

Written by

Software Engineer | Co-Founder @ tripapt.com | Need a bug fixed? Hire me https://www.fiverr.com/share/D5RzZD

The Startup

Get smarter at building your thing. Follow to join The Startup’s +8 million monthly readers & +788K followers.

Lewis Fairweather

Written by

Software Engineer | Co-Founder @ tripapt.com | Need a bug fixed? Hire me https://www.fiverr.com/share/D5RzZD

The Startup

Get smarter at building your thing. Follow to join The Startup’s +8 million monthly readers & +788K followers.

Medium is an open platform where 170 million readers come to find insightful and dynamic thinking. Here, expert and undiscovered voices alike dive into the heart of any topic and bring new ideas to the surface. Learn more

Follow the writers, publications, and topics that matter to you, and you’ll see them on your homepage and in your inbox. Explore

If you have a story to tell, knowledge to share, or a perspective to offer — welcome home. It’s easy and free to post your thinking on any topic. Write on Medium

Get the Medium app

A button that says 'Download on the App Store', and if clicked it will lead you to the iOS App store
A button that says 'Get it on, Google Play', and if clicked it will lead you to the Google Play store