Your first performance budget with Lighthouse

I asked on Twitter the other day how many people had created and enforced a performance budget for a website they were working on. Not surprisingly, the vast majority of people hadn't.

I'm curious, have you ever created (and enforced) a performance budget for a site you're working on? — Ire Aderinokun (@ireaderinokun) May 24, 2019

Until recently, I also hadn't setup an official performance budget and enforced it. This isn’t to say that I never did performance audits. I frequently use tools like PageSpeed Insights and take the feedback to make improvements. But what I had never done was set a list of metrics that I needed the site to meet, and enforce them using some automated tool.

The reasons for this were a combination of not knowing what exact numbers I should use for budgets as well as there being a disconnect between setting a budget and testing/enforcing it. This is why I was really excited when, at Google I/O this year, the Lighthouse team announced support for performance budgets that can be integrated with Lighthouse. We can now define a simple performance budget in a JSON file, which will be tested as part of the lighthouse audit!

The Lighthouse performance budget #

As we know, there are countless performance metrics out there. From user-centric milestones such as Time to Interactive, to resource-centric metrics such as the size of your javascript files.

The performance budget we can set on Lighthouse focuses on the latter and is purely based on the raw values of your website’s assets and resources. There are two types of budgets we can create:

  1. The number of a given resource - e.g., a budget which enforces that only 2 javascript files be loaded by the given page
  2. The size of a given resource - e.g., a budget which enforces that the given page only loads 500kb of javascript

Creating the budget.json #

Lighthouse expects the performance budget to be written in a JSON file, typically named budget.json.

The JSON file is setup as an array of objects, each object being a set of budgets for a single path. It should be noted that currently, Lighthouse only supports one set of budgets for one path, which means that the array in budgets.json should only have one object. However, the intention is that we'll be able to specify budgets for different paths in a single file, so it's setup this way for future proofing.

The main budget object is organised by budget type (resourceCounts or resourceSizes), each containing an array of budgets for each type of resource. For example, let’s create a budget.json that enforces the following budget -

  1. 10 third-party resources
  2. 300kb Javascript
  3. 100kb CSS

Here’s what the corresponding budget.json would look like:

[
{
"resourceCounts": [
{"resourceType": "third-party","budget": 10}
],
"resourceSizes": [
{"resourceType": "script","budget": 300},
{"resourceType": "stylesheet","budget": 100}
]
}
]

The following resource types are available:

Resource type Description
document HTML documents
script Javascript files
stylesheet CSS files
image Images
media Other media
font Webfonts
other Any resources that don’t match the above, e.g. data transfers over Websocket connections
third-party All resources from a third-party domain
total All resources combined

Choosing a performance budget #

Now that we know how to create a performance budget, the next question is what should we put in it? Although the answer to this will change dramatically depending on the specifics of your site, you can use this Performance Budget Calculator to get an idea of what different budgets will mean for user-centric metrics such as time to interactive.

For the example, the default budget below will result in an estimated 4.4s time to interactive:

[
{
"resourceSizes": [
{"resourceType":"document","budget":20},
{"resourceType":"stylesheet","budget":50},
{"resourceType":"font","budget":50},
{"resourceType":"image","budget":300},
{"resourceType":"script","budget":100}
]
}
]

Enforcing the performance budget with Lighthouse #

At the moment, the performance budget can only be consumed by the Lighthouse CLI. This means that we can’t yet use it with the in-browser audit panel or online tools like PageSpeed Insights or Web.dev. These integrations are being worked on, but for now, there are primarily 2 ways you’ll want to use the Lighthouse performance budget.

Basic command line usage #

The simplest way is to install the Lighthouse CLI, and run the audit command, passing in your budget.json file as an option.

lighthouse [url] --budget-path=[path/to/budget.json]

For example:

lighthouse https://bitsofco.de --budget-path=budget.json

This command will trigger the lighthouse audit and will output the typical lighthouse results page with one addition - a section on how your page performs against your specified budgets.

Lighthouse results with budgets

Continuous integration #

Because the audits are available using the command line interface, they can be used wherever the CLI can be installed. This means we can include it in our continuous integration process.

There’s an excellent article on web.dev that shows how you can setup the Lighthouse Bot to run checks against GitHub Pull Requests.

Lighthouse audit check on Github

Image from github.com/GoogleChromeLabs/lighthousebot

This is probably the best way to set things up so the checks happen automatically.

Keep in touch KeepinTouch

Subscribe to my Newsletter 📥

Receive quality articles and other exclusive content from myself. You’ll never receive any spam and can always unsubscribe easily.

Elsewhere 🌐