Quick & Easy CSS Compression Using PHP

Loading time of a website is as important as its functionality. You can have a great website but who wants to wait for it to load? CSS compression can help your website load faster and easily maintain its functionality. I've created an easy-to-use PHP file to compress your CSS for optimal client download time.

The Code

The process takes place in two files: one PHP file which we call css.css (yes, use the ".css" extension) and your directory's .htaccess file.

Here's the PHP for css.css:

$css = '';
$root = $_SERVER['DOCUMENT_ROOT'].'/css/'; //directory where the css lives
$files = explode(',',$_SERVER['QUERY_STRING']);
if(sizeof($files))
{
	foreach($files as $file)
	{
		$css.= (is_file($root.$file.'.css') ? file_get_contents($root.$file.'.css') : '');
	}
}
return str_replace('; ',';',str_replace(' }','}',str_replace('{ ','{',str_replace(array("\r\n","\r","\n","\t",'  ','    ','    '),"",preg_replace('!/\*[^*]*\*+([^/][^*]*\*+)*/!','',$css)))));

The css.css file takes the given querystring and explodes it on a comma into an array. If there is something in the querystring (which there should be, unless the programmer messes up), which should be separated by a comma, the querystring gets separated into an array. For each string within the array, the script looks for a CSS file with a matching name. The script then appends the content of the file to a string variable ($css). Once all of the CSS content is within the $css variable, the CSS content is scrubbed of all whitespace. Less whitespace and one file means a much faster download speed since there is only one request for a compressed file.

Here's the code you'll place into the .htaccess file so that css.css gets treated as a PHP file:

<FILES css.css>
  SetHandler  application/x-httpd-php
</FILES>

The Usage

Using the css.css file is easy:

<link href="/css/css.css?reset,base,forms,template" rel="stylesheet" type="text/css" media="screen" />

Essentially, in the example above, we're looking to use reset.css, base.css, forms.css, and template.css. If one of those files doesn't exist, they wont be added (and there's no error message).

Do you have any suggestion for my script? Any ideas to contribute that would optimize the CSS?


Comments

  1. Jesus D

    What about the performance of this script?
    I can imagine the concatenating the $css can get quite expensive. Maybe add some caching mechanism that wont have to reread the files and perform that nasty string replace.

    Just a suggestion. :)

  2. david

    Thank you for contributing Jesus.

    It all depends on how frequently you update your CSS.

    You could definitely save the output of this script and simply reference that.

    David

  3. James

    Cool script. Depending on the size of the site, I find it most efficient to incorporate the CSS packing during the build process, and release as a static CSS file. Then configure Apache to gzip output of CSS files to shrink even further ;)

  4. Andreas

    Nice! Just what I was looking for.

  5. Christine Furst

    What a pitty. My webserver ( one.com ) does not seem to support this usage of the .htaccess file. :-(
    Cheers, Stinie

  6. Thomas Wilhelm

    I added some code and I think it improved the compression a little bit:
    [code]$css = str_replace(': ', ':', str_replace(';}', '}', str_replace('; ',';',str_replace(' }','}',str_replace(' {', '{', str_replace('{ ','{',str_replace(array("\r\n","\r","\n","\t",' ',' ',' '),"",preg_replace('!/\*[^*]*\*+([^/][^*]*\*+)*/!','',$css))))))));[/code]

  7. tutoriale pc

    I’ve used this script on my website. Thanks!

  8. M1ke

    Thanks, this code (and the idea behind it) was very useful. I had to change how it was output as originally the browser wouldn’t read it – could have been due to server settings. I just added this to the end:
    header("Content-type: text/css");
    echo $css

    Also the code Thomas Whilhelm posted was useful, it did shave an extra kB off the document but only after I removed the 5-7th elements of the 7th str_replace:
    $css=str_replace(': ', ':', str_replace(';}', '}', str_replace('; ',';',str_replace(' }','}',str_replace(' {', '{', str_replace('{ ','{',str_replace(array("\r\n","\r","\n","\t"),"",preg_replace('!/\*[^*]*\*+([^/][^*]*\*+)*/!','',$css))))))));
    With those extra elements (which came out as spaces on here) it messes up any nested CSS (i.e. most of it)

  9. CJ

    I simplified it even further and cut out as much whitespace as possible with this code. I’ve rearranged the spaghetti into a function just because I prefer it that way. Feel free to re-spaghetti.


    function compress($css){
    // Remove comments
    $css = preg_replace('!/\*[^*]*\*+([^/][^*]*\*+)*/!', '', $css);
    // Remove spaces before and after symbols
    $css = preg_replace('/(\s(?=\W))|((?<=\W)\s)/', '', $css);
    // Remove remaining whitespace
    $css = str_replace(array("\r\n","\r","\n","\t",' ',' ',' '), '', $css);
    return $css;
    }

  10. Lyricstub

    Extremely simple to implement, I tried code.google.com/p/minify/ but it is very hard to adopt and implement.
    Your code is so simple and light weight to implement.
    It will be implemented in next release of my product.

    It would be appreciated if you can help me understand: what is difference between css.css to be treated as PHP rather than url rewriting?

    Cheers!!!

  11. JmsRie

    Super helpful..
    need also to add this bit of code in order to work maybe due to some server settings like M1ke did. Thanks a lot!!

    header("Content-type: text/css");

  12. Roman

    Thanks for codes,…

    but i created my own compressor.
    http://www.igloro.info/en/css_compressor.html


Be Heard!

Share your thoughts without being a jerk! And wrap your code in <code> tags, f00!

Name*:
Email*:
Website: