CSS stylesheets are one of the core technologies powering the web. This article explains why optimizing is important for page speed and what you can do to reduce CSS size. We'll also introduce the free CSS Size Analyzer.
Why does CSS page weight have a big impact on page load time?
Most CSS stylesheets are render-blocking which means that users can't see any page content until after they've been loaded.
You can see an example of this in the request waterfall below:
- The HTML document is loaded
- The document contains a
linktag to the CSS stylesheet
- The browser downloads the stylesheet
- After downloading the stylesheet the browser renders the page and the content becomes visible to the visitor
The blue line in the waterfall chart indicates the First Contentful Paint. You can see that this happens after the download of the CSS is complete.
Therefore loading CSS quickly is important to reduce overall page load time.
What can you do to optimize your CSS for speed?
To load CSS more quickly you can:
- Reduce CSS download size
- Load CSS code from your own domain
Reducing CSS download size
The download size of a CSS file depends both on its content and on how it's served to the browser.
Compress and minify your CSS
Your server should be set up to apply Brotli or gzip compression before transferring the CSS stylesheet.
You can also minify your CSS to reduce its size without changing what it does. While Broli and gzip are generic text compression algorithms, minification is aware of CSS syntax and can therefore identify other optimizations.
Don't embed images or fonts in your CSS code
It's possible to use data URLs and Base64 encoding to embed images and other resources in your CSS code:
Image files are often large and take more time to download. Normally they are not render-blocking, but if they are embedded in a stylesheet they do block render and content takes longer to appear for users.
With modern front-end tooling it can be easy to accidentally embed a large image without noticing. Our CSS Size Analyzer can detect embedded resources automatically:
Avoid long CSS selectors
Tools like Less CSS make it easy to nest CSS code and accidentally create very long CSS selectors.
For example, here you can see a CSS selector with a length over 10,000 characters:
However, due to the repetitive nature of the selector this can be compressed to 669 bytes. Still a lot for a single selector, but it will only become a problem if you have many selectors like that.
Check whether the CSS code needed on the page
Chrome DevTools provides a code coverage tool that can tell you whether the CSS rules in your stylesheets are actually used on the current page.
You can open the tool via the three dots on the top right of Chrome DevTools:
Then click the reload button and Chrome will show you what percentage of CSS is in use by the page. You can open the CSS files it analyzed to see which rules are in used and which aren't.
Note that Chrome only measures usage for that particular page load. Different CSS rules will be used by different pages, on different devices, and depending on what pages elements were shown to the user.
Break down CSS size with the CSS Size Analyzer
The CSS Size Analyzer is a free tool that finds the largest CSS rules in your stylesheets and highlights common issues like embedded images. You can then use this information to fix large CSS files on your website.
Load CSS code from your own domain
To load a resource from a server browsers first need to establish a connection to that server. This takes time and will be slower on a high-latency network connection.
You can see an example here, where the HTML is loaded from
www.shopify.com and the CSS is loaded from
cdn.shopfiy.com, requiring a new connection. You can see the connection being created by looking at the teal, orange, and purple markers.
Loading CSS from your the same domain as the HTML will be quicker as the existing server connection can be reused.
Avoid @import rules
@import rules are a way to reference a CSS file from with a CSS file:
However, this is not advisable from a page speed perspective as
@import creates sequential render-blocking request chains.
In this example waterfall the Google Fonts CSS is loaded via the assets CSS file. That means the download only starts after the other file has been loaded.
Loading CSS asynchronously
Loading CSS asynchronously means loading styles without blocking rendering. Generally this is undesirable as you don't want visitors to see your website without any styles. Users would experience a flash of unstyled content and when the styles are loaded the page layout would change.
However, it can be useful for less important styles, for example for a widget that's shown far down the page.
One way to load styles asynchronously is by initially telling Chrome that the styles only apply when printing the page. That way the CSS won't block rendering.
Then, when the
onload event fires the
media attribute is change to apply to all media types. At this point the stylesheet applies like any other CSS file.
Should you inline CSS in your HTML?
You can use
style tags within your HTML code to embed CSS styles directly in the document. That way no additional render-blocking network requests are required.
This is a good idea for small amounts of CSS, maybe below 5 to 10 kilobytes.
However, CSS inside the HTML has to be reloaded every time the user navigates to a new page. A standalone CSS file can be cached by the browser and re-used for the next page.
Therefore it is better to keep larger CSS files separate from your HTML.
How big should a CSS file be?
There's no single number, but I would say that less than 20 kilobytes is very good and I wouldn't worry until a CSS file reaches 50 to 100 kilobytes.
How do I know if CSS is slowing down my website?
Run a free website speed test and then look at the request waterfall to see what's holding your website back. If you notice slow initial rendering then that can often be caused by render-blocking CSS.
You can also use DebugBear to continuously monitor page speed, page weight, and Lighthouse scores.