Understanding CSS minification
Whitespace out, semantics in.
What a CSS minifier does mechanically, the few real optimisations it makes beyond whitespace, and what cssnano adds.
The five free wins.
A minimal CSS minifier strips: leading/trailing whitespace, internal whitespace between selectors and braces, comments (unless marked /*! */), the last semicolon in a rule, redundant zero units (0px → 0). Pure mechanical transformations; can't change semantics. Saves 10-30 % on hand- written CSS, less on already-tidy CSS.
The cleverer wins.
A smarter minifier (cssnano, clean-css) goes further. Colour normalisation: #ffffff → #fff; rgb(255, 255, 255) → #fff. Property shortening: margin: 10px 10px 10px 10px→ margin: 10px. Selector merging: duplicate rules combined. Vendor-prefix removal for browsers no longer supported. These need parsing the CSS, not just string-stripping; they're the difference between basic and modern minifiers.
A worked minify.
Input: .card {
color: #ff0000;
background: rgb(255, 255, 255);
margin: 10px 10px 10px 10px;
/* edge case */
padding: 0px;
} Output: .card{color:red;background:#fff;margin:10px;padding:0}. From 130 bytes to ~60 bytes; same rendered result.
Six transforms in one line
whitespace + comments + colour + shorthand + 0px + final semicolon
Each transform is small; the combined effect is dramatic.
130 bytes → 60 bytes
= >50 % reduction
Gzip eats most of the win.
Both the original and the minified CSS go through gzip before they hit the wire. Gzip is very good at compressing repeated text — so the whitespace and long property names compress similarly in both versions. The minified file is still smaller on the wire, but by less than the raw byte count suggests (often 5-10 % gzipped, not 50 %). Real savings: parse time on the client (CSS parsing is single-threaded; less to parse is faster).
Source maps.
Minified CSS is unreadable. Source maps (.css.map) tell DevTools the mapping from minified bytes back to the original source — set a breakpoint on a rule in DevTools, jump to the right line in your source CSS. Modern minifiers emit source maps by default; serve them in development, strip in production (they're an information leak about your source structure).
Tailwind doesn't need this much.
Tailwind v3's JIT generates only the classes you use, so the output CSS is already small. Tailwind v4 ships even less. For a Tailwind project, additional minification beyond the framework's own optimisation is single-digit percent. For projects with hand-written CSS or large stylesheets imported from third- party libraries, the minifier still matters.