How to tree shake / subset Font Awesome 5 icons

Learn how to tree shake FontAwesome 5 icons with Webpack.

The current FontAwesome 5 Free SVG JS file size is over 1mb. FontAwesome Pro is almost 3mb! There’s no way any single application will be using all of those awesome icons. I wouldn’t even say that they’re using a quarter of them. What does this mean? It means you’re having a user load over 1mb of icons only to use, at most, 80kb of them. No good. I am going to show you how to tree shake or subset the SVG icons only used in your app.

Prerequisites:

Getting Started

We’ll be using Node.js with npm to install Webpack (globally) which can utilize the tree shaking technique in JavaScript. If all those words just confused you, don’t fret. It’s mostly copy/pasting commands to get it working.

1.) Create new directory and initialize npm & webpack

We need to create a new directory and initialize npm to house all the packages and final icons file.

mkdir fa-icons
cd fa-icons && npm init

Install webpack.

npm install --save-dev webpack

2.) Import FontAwesome

Import the core JS functions that FontAwesome uses as well as the icon packs we want to use.

npm install @fortawesome/fontawesome-svg-core

Now add the icons we want to use. Here, I am importing all of FontAwesome’s 5 free icons and all their respective weight types (regular and solid).

npm install --save-dev @fortawesome/free-regular-svg-icons
npm install --save-dev @fortawesome/free-solid-svg-icons
npm install --save-dev @fortawesome/free-brands-svg-icons

4.) Import icons

Open your main JS entry point. Normally, index.js is located in the src folder. If you don’t have one, create it. This is where each icon will be added and imported from the previous packages we installed. Notice each icon weight needs to be imported from their own package (brands also).

import { library, dom } from '@fortawesome/fontawesome-svg-core'

// Import solid weight icons
import {
    faUser as fasUser,
    faUserCircle as fasUserCircle
} from '@fortawesome/free-solid-svg-icons'

// Import regular weight icons
import {
    faUser as farUser,
    faUserCircle as farUserCircle
} from '@fortawesome/free-regular-svg-icons'

// Import brand icons
import {
    faWordpress as fabWordpress
} from '@fortawesome/free-brands-svg-icons';

// Add icons to library
library.add(
    // Solid
    fasUser,
    fasUserCircle,

    // Regular
    farUser,
    farUserCircle,

    // Brands
    fabWordpress
)

// Replace any existing <i> tags with <svg> and set up a MutationObserver to
// continue doing this as the DOM changes.
dom.watch()

5.) Replace Webpack 4’s default minifier (optional)

The default minifier used in Webpack 4 seems to have problems with Font Awesome causing a very slow build time. The fix for this is to switch the minifier to Babel minify plugin instead.

Install the Babel minifier package.

npm install --save-dev babel-minify-webpack-plugin

Create a file called webpack.config.js in your root directory and paste the following:

// webpack.config.js
const BabelMinifyPlugin = require('babel-minify-webpack-plugin')
module.exports = {
  entry: './src/index.js',
  output: {
    filename: './fontawesome.js'
  },
  optimization: {
    minimizer: [
      new BabelMinifyPlugin()
    ]
  }
}

5.) Build

After you added all the icons you want to use in your app you can now build.

webpack

Once the build is complete you’ll find your icons inside dist folder! You can now copy/paste and link that file into your app the same way you would with FontAwesome JS but now with a much smaller file size.

Conclusion

Although FontAwesome icons are quite awesome! There’s no need to load all 1mb (3m) of them. FontAwesome does plan to add easier subsetting in the future. This is also not the only way to reduce icons and files size but I find it the most convenient and maintainable.

Justin Mathew

A front end web developer specializing in HTML/CSS, JS, PHP & MySQL with over 10 years experience in the web development field.