A low Google PageSpeed score isn't just a vanity metric — it directly affects your search rankings, your bounce rate, and how many visitors stick around long enough to become customers. Google has confirmed that Core Web Vitals are a ranking factor, and the data is unambiguous: faster sites rank higher, convert better, and retain more visitors.
To improve your Google PageSpeed score, optimize your Largest Contentful Paint (LCP) by compressing images and improving server response time, reduce Total Blocking Time (TBT) by deferring non-critical JavaScript, fix Cumulative Layout Shift (CLS) by adding explicit image dimensions, enable browser caching, and preconnect to critical third-party origins.
Quick actions to improve your Google PageSpeed score:
- Compress hero images and convert them to WebP or AVIF
- Add
deferorasyncto non-critical JavaScript - Set explicit width and height on all images and videos
- Enable server-side page caching and use a CDN
- Preconnect to fonts and third-party script origins
But knowing your score is bad and knowing what to do about it are two different problems. This guide gives you the complete workflow — from getting your baseline score to fixing the issues that move the needle.
Step 1: Get Your Baseline Score
Before you can improve your PageSpeed score, you need to know where you're starting. You need two things: your overall score and a breakdown of which issues are driving it down.
Run a WebsiteLinter scan first at websitelinter.com. The free scan gives you:
- Your PageSpeed score (mobile and desktop separately)
- Core Web Vitals: LCP, INP, and CLS with pass/fail thresholds
- Performance grade with specific diagnostic findings
This gives you a unified baseline that includes both performance and SEO/security context — so you understand whether your speed issues are isolated or part of a broader site health problem.
Then run Google PageSpeed Insights at pagespeed.web.dev for the full diagnostic breakdown. This gives you the Lighthouse audit with specific "Opportunities" and "Diagnostics" sections that show exactly which elements are slow and how much time each fix would save.
Write down your starting scores. You'll want to compare after each round of fixes.
Step 2: Understand What the Score Actually Measures
The PageSpeed score (0–100) is a weighted composite of six performance metrics measured in lab conditions:
| Metric | Weight | What It Measures |
|---|---|---|
| First Contentful Paint (FCP) | 10% | When the first text/image appears |
| Speed Index (SI) | 10% | How quickly content visually fills the page |
| Largest Contentful Paint (LCP) | 25% | When the largest visible element loads |
| Total Blocking Time (TBT) | 30% | How long the main thread is blocked by JS |
| Cumulative Layout Shift (CLS) | 15% | How much the layout shifts during load |
| Interaction to Next Paint (INP) | 10% | Page responsiveness to user input |
LCP and TBT together account for 55% of your score. If your score is low, start there.
Step 3: Fix LCP — The Biggest Single Win
Largest Contentful Paint (LCP) measures how long it takes for your largest visible content element to load — usually a hero image, a banner, or a large heading. Google's threshold for "Good" LCP is under 2.5 seconds.
Identify your LCP element
In Chrome DevTools, open the Performance tab and run a recording. Look for the "LCP" marker in the timeline. Alternatively, PageSpeed Insights labels it directly in the audit.
The most common LCP fixes:
1. Optimize your hero image
Your hero image is almost always the LCP element. Every one of these matters:
- Convert to WebP or AVIF format — WebP is 25–35% smaller than JPEG at the same quality; AVIF is even smaller
- Set explicit width and height attributes — prevents layout shift and helps the browser allocate space before the image loads
- Use responsive images (
srcset) — serve smaller images to smaller screens - Don't lazy-load the LCP image — lazy loading is great for below-the-fold images but delays your LCP element
2. Add fetchpriority="high" to your LCP image
<img src="hero.webp" fetchpriority="high" alt="Hero image" width="1200" height="600">
This single attribute tells the browser to fetch this image before other resources. It's often a 200–500ms improvement.
3. Improve Time to First Byte (TTFB)
If your server response time is above 600ms, everything downstream gets delayed. Check TTFB in PageSpeed Insights under "Server response times." Common causes: unoptimized database queries, no page caching, or underpowered hosting.
- Enable page caching (WordPress: WP Rocket, W3 Total Cache; others: server-level caching)
- Use a CDN to serve assets from edge nodes closer to your visitors
Step 4: Reduce Total Blocking Time (TBT)
TBT measures how long JavaScript execution blocks the main thread, preventing the browser from responding to user input. High TBT makes your site feel slow even if it loads quickly visually.
The main causes of high TBT:
Render-blocking scripts:
Scripts loaded in the <head> without async or defer attributes block parsing. Add defer to non-critical scripts:
<!-- Blocking -->
<script src="analytics.js"></script>
<!-- Non-blocking -->
<script src="analytics.js" defer></script>
Unused JavaScript:
Modern sites often load entire JavaScript libraries when they only use a small portion. PageSpeed Insights shows "Reduce unused JavaScript" with estimated savings. Key fixes:
- Remove unused plugins and scripts entirely
- Use tree-shaking in your build process to eliminate dead code
- Load third-party scripts (analytics, chat widgets, ad tags) after page load
Long tasks:
A "long task" is any JavaScript execution that takes more than 50ms. They block the main thread and inflate TBT. Chrome DevTools' Performance tab shows long tasks in orange in the timeline.
Step 5: Fix CLS — Stop Your Page From Jumping
Cumulative Layout Shift (CLS) measures unexpected movement of page elements during load. A high CLS score means buttons, images, or text are shifting positions while the user is trying to interact — which is frustrating and sometimes causes accidental clicks.
Common CLS causes and fixes:
Images and video without dimensions:
<!-- Bad: browser doesn't know how much space to reserve -->
<img src="product.jpg" alt="Product">
<!-- Good: browser reserves space before image loads -->
<img src="product.jpg" width="800" height="600" alt="Product">
Fonts causing layout shift:
When a system font is displayed before your custom font loads, text can reflow when the custom font kicks in. Fix with font-display: optional or font-display: swap with proper fallback font sizing.
Late-injected content:
Ads, banners, and newsletter popups injected after load push existing content down. Always pre-reserve space for dynamically injected elements.
Step 6: Address the Long Tail Issues
Once LCP, TBT, and CLS are in good shape, these secondary improvements push your score higher:
Eliminate render-blocking resources:
CSS in the <head> blocks rendering. For critical CSS, inline it directly in the HTML. For non-critical CSS (below-the-fold styles), load it asynchronously.
Properly size and compress all images:
Every image that's larger than its display size wastes bandwidth. In WordPress, plugins like ShortPixel or Imagify handle this automatically. In custom builds, add image optimization to your build pipeline.
Implement effective caching:
Set Cache-Control headers so returning visitors don't re-download static assets. Typical targets:
- Images: 1 year
- CSS/JS with content hashing: 1 year
- HTML: short (1 hour or no-store for dynamic content)
Preconnect to critical third-party origins:
If your page loads fonts from Google Fonts or scripts from a CDN, add <link rel="preconnect"> in the <head>:
<link rel="preconnect" href="https://fonts.googleapis.com">
<link rel="preconnect" href="https://fonts.gstatic.com" crossorigin>
Step 7: Validate With a Re-Scan
After each round of changes, re-run your WebsiteLinter scan and PageSpeed Insights. Look for:
- Did your LCP improve? It should drop if you optimized your hero image.
- Did TBT drop? It should if you deferred scripts or removed unused JS.
- Did your overall score change? Sometimes a single fix moves the needle significantly.
Don't try to fix everything at once. Make changes in batches, re-test, and confirm the impact before moving to the next batch. This makes it easy to identify which specific changes made a difference.
Realistic Score Expectations
| Starting Score | Realistic Target | Typical Effort |
|---|---|---|
| 20–40 | 60–75 | Medium — usually has major image or JS issues |
| 40–60 | 75–85 | Moderate — several specific optimizations needed |
| 60–75 | 85–95 | Low-medium — targeted fixes to LCP/TBT |
| 75–85 | 90–95 | Low — fine-tuning, caching, preloading |
Getting from 90 to 100 is often disproportionately difficult and not worth the effort. The ranking benefit plateaus well before 100.
The Right Starting Point
You can't fix what you haven't measured. The workflow above works, but only once you have a clear picture of your site's current state — what your scores are, which metrics are failing, and what specific elements are causing them.
Start with a free WebsiteLinter scan at websitelinter.com — get your PageSpeed score, Core Web Vitals, and a full health report in under two minutes. No account, no credit card. Then come back to this guide and start working through the fixes.