Use a performance budget to assert thresholds for performance metrics. budget.json
supports three types of budgets:
- Timing budgets: Assert thresholds for time-based performance metrics like First Contentful Paint, Maximum First Input Delay, and Speed Index.
- Resource counts: Assert thresholds for the quantity of resources on a page. These thresholds can be defined per resource type or for the page overall.
- Resource sizes: Assert thresholds for the transfer size of resources on a page. These thresholds can be defined per resource type or for the page overall.
If performance budgets have been configured, the Lighthouse report will include a "Performance Budgets" section.
To make performance budgets a part of your CI process, refer to Lighthouse CI.
Performance budgets are supported in the CLI version of lighthouse. To use:
- Create a
budget.json
file. - When running Lighthouse from the command line, pass the
--budget-path
flag followed by the path to budget file in order to calculate whenever a category is over budget.
lighthouse https://youtube.com --budget-path=budget.json
Performance budgets can also be defined on the Lighthouse config for usage with the Node API:
import lighthouse from 'lighthouse';
const config = {
extends: 'lighthouse:default',
settings: {
budgets: [
{
path: '/*',
resourceSizes: [
{
resourceType: 'script',
budget: 200
}
]
}
]
}
}
await lighthouse('https://example.com', undefined, config);
The budget.json
file is an array containing one or more Budget
objects.
[
{
"path": "/*",
"options": {
"firstPartyHostnames": ["*.my-site.com", "my-site.cdn.com"]
},
"timings": [
{
"metric": "interactive",
"budget": 5000
},
{
"metric": "first-meaningful-paint",
"budget": 2000
}
],
"resourceSizes": [
{
"resourceType": "total",
"budget": 500
},
{
"resourceType": "script",
"budget": 150
}
],
"resourceCounts": [
{
"resourceType": "third-party",
"budget": 100
}
]
},
{
"options": {
"firstPartyHostnames": ["*.my-site.com", "my-site.cdn.com"]
},
"path": "/checkout",
"resourceSizes": [
{
"resourceType": "script",
"budget": 200
}
]
}
]
Lighthouse 6 & up
Use the optional timings
property to define budgets for time-based performance metrics. In this context, budgets are defined in milliseconds.
"timings": [
{
"metric": "interactive",
"budget": 5000
}
]
Supported timing metrics:
first-contentful-paint
interactive
first-meaningful-paint
max-potential-fid
total-blocking-time
speed-index
largest-contentful-paint
cumulative-layout-shift
Use the optional resourceSizes
property to define budgets for the size of page resources. In this context, budgets are defined in kibibytes (1 KiB = 1024 bytes).
"resourceSizes": [
{
"resourceType": "script",
"budget": 300
}
]
Use the optional resourceCounts
property to define budgets for the quantity of page resources. In this context, budgets are defined in # of requests.
"resourceCounts": [
{
"resourceType": "script",
"budget": 10
}
]
Budgets can be set for the follow resource types.
document
font
image
media
other
script
stylesheet
third-party
total
Lighthouse 5.3 & up
The path
property indicates the pages that a budget applies to. This string should follow the robots.txt format.
If path
is not supplied, a budget will apply to all pages.
If a page's URL path matches the path
property of more than one budget in budget.json
, then the last matching budget will be applied. As a result, global budgets (e.g. "path": "/*"
) should be listed first in budget.json
, followed by the budgets that override the global budget (e.g. "path": "/blog"
).
Examples:
"path": "/"
Result: Matches all URL paths. This is equivalent to writing "path": "/*"
"path": "/articles"
Result: Matches all URL paths starting with /articles
. For example, /articles
and /articles/jun_02_2019.html
"path": "/store/*/details$"
Result: Matches /store/clothes/item123/details
but does not match /store/details
.
Lighthouse 6 & up
options.firstPartyHostnames
can be used to indicate which resources should be considered first-party. Wildcards can optionally be used to match a hostname and all of its subdomains.
If this property is not set, the root domain and all its subdomains are considered first party.
"options": {
"firstPartyHostnames": ["*.my-site.com", "my-site.cdn.com"]
}
Examples:
"firstPartyHostnames": ["pets.com"]
Result: pets.com is considered first-party, but fishes.pets.com is not.
"firstPartyHostnames": ["*.pets.com"]
Result: Both pets.com and fishes.pets.com are considered first party.