The page ships more JavaScript than it uses
What this check looks for
This page downloads ‹total js› of JavaScript, of which roughly ‹unused bytes› is never executed during the page load. Every byte of it is parsed and compiled before it can be ignored.
Why it matters
JavaScript is the most expensive thing a page can download: unlike an image, it has to be parsed, compiled and executed on the main thread — the same thread that has to respond when the visitor taps something.
When the check passes, your report says: “The page ships close to the JavaScript it actually uses”.
What it costs your score
When this check fails it removes 8 points from your Performance score, before the status, confidence and repeat multipliers are applied. Performance carries a weight of 8 in the overall score.
It shares the performance.assets family ceiling of 25 points: however many findings that family produces, together they cannot remove more than that from Performance. One underlying problem showing up in several places is still one problem.
- Severity
- medium
- Default confidence
- high
- Status when triggered
- warn
- Deduction
- 8 points
- Family cap
- performance.assets · 25
- Category
- Performance
- Module
- Perf lab
- Fix owned by
- user
- In the ruleset since
- 2026.09
How to fix it
Ship only the JavaScript this page needs to render and respond, and load the rest on demand.
Roughly ‹unused bytes› of downloaded JavaScript never runs during the load, and the main thread pays to parse and compile all of it before it can find that out.
Split the bundle by route, so a visitor to one page does not download the code for the rest of the site.
Load interaction-only code on the interaction — dynamic
import()inside the event handler is enough, and the network cost lands when the user has already committed.Audit third-party scripts against what they earn. In Chrome DevTools, Coverage shows the unused share per file; anything above 80% unused is a candidate for removal or deferral.
Defer everything that is not needed for the first render, so parsing does not compete with the initial paint.
Check for duplicated dependencies across chunks — shipping two copies of the same library is common and invisible without looking.
How to confirm it worked
Re-run this scan and confirm the transferred JavaScript total and the unused share have dropped.
In Chrome DevTools, open Coverage, reload, and confirm the unused bytes figure has fallen.
A named slot like ‹domain› — and the braces left in the configuration below — is filled in with your own values when this rule appears on a report.
Remediation by platform
// Ship the code for an interaction when the interaction happens.
button.addEventListener('click', async () => {
const { openEditor } = await import('./editor.js');
openEditor();
}, { once: true });
<!-- And keep what does load out of the critical path. -->
<script src="/analytics.js" defer></script>{ once: true }avoids re-importing on every click; the module cache would make that cheap anyway, but the intent is clearer. The win is thateditor.jsis never fetched by the visitors who never open the editor.
Technical detail
JavaScript transferred: **‹total js›** across ‹script count› script(s); unused on load: **‹unused bytes›** (‹unused percent›%).
‹detail›
This came from **one page load we performed**, not from your visitors. A lab measurement is reproducible and tells you exactly which bytes and which resources are responsible — which is why the numbers below are byte counts and resource lists rather than a score. What real visitors experience is in the field-data section, which is the evidence this report scores Core Web Vitals on.
"Unused" here means the bytes were never executed during the page load. Some of that is legitimate — code behind an interaction that has not happened yet — so this is not a demand to delete it, it is a demand to **stop shipping it up front**. The distinction is code splitting, not code removal.
This is also the metric most directly connected to Interaction to Next Paint. Parse, compile and execution all occupy the main thread, and a visitor who taps during that work waits for it to finish before anything responds. If the field data in this report shows a poor INP, this finding is usually where the cause is.
Third-party scripts are worth a separate look: they are frequently the largest single contributor, they are rarely code-split, and they are the easiest to defer because the page does not depend on them to render.
Standards and references
Test this on your domain
Run the check that produces this finding, on its own, against any domain.
Other perf lab checks
- Images are served in older, heavier formats
- Images are much larger than the space they are shown in
- Lab measurement of one page load
- Stylesheets and scripts stop the page from rendering
- This report never publishes a headline performance score
- Static files are re-downloaded because they are barely cached
- Scripts and stylesheets are sent without compression
- The page was not measured in a browser