Compress and output CSS

Have you ever wanted to reduce the size of your CSS files that you serve to your visitors? If so then here is a quick solution to it. This function will remove all unnecessary spaces, tabs, new line characters as well as multi- and single-line comments reducing the size of your CSS file quite significantly.

Here is the function source:

  1. <?php
  2.  
  3. /**
  4.  * Compress contents of a CSS file
  5.  *
  6.  * @param string $css Contents of a css file
  7.  * @return string
  8.  */
  9. function compressCss($css)
  10. {
  11.     // remove multiline comments, new lines, tabs and single line comments
  12.     $css = preg_replace_callback('/(\/\*.*?\*\/|\n|\t|\/\/.*?\n)/sim',
  13.         create_function(
  14.             '$matches',
  15.             'return "";'
  16.         ), $css);
  17.  
  18.     // remove all around in ",", ":" and "{"
  19.     $css = preg_replace_callback('/\s?(,|{|:){1}\s?/sim',
  20.         create_function(
  21.             '$matches',
  22.             'return $matches[1];'
  23.         ), $css);
  24.  
  25.     return $css;
  26. }

As you can see the function consists of two steps:

  1. remove all multi-line comments, new line characters, tabs and single-line comments
  2. remove wrapping spaces around commas, colons and left curly braces

Further follows a small example on how you could use this function in a "compressor" file that accepts a list of files and compresses and outputs them.

Let's call the file css.php. It has to accept one GET parameter (let's call it files). The list of files would have to be names of our css files (without extensions) separated by commas. We don't want the extensions because first, we know that they will always be .css and second, hackers could potentially read contents of other system files by doing something like "css.php?files=../../.htaccess" or similar if we accepted names of existing files.

  1. <?php
  2.  
  3. // start output compression
  4. if (extension_loaded('zlib')) {
  5.     ob_start('ob_gzhandler');
  6. }
  7.  
  8. // send css headers
  9. header('Content-Type: text/css');
  10.  
  11. // get the list of files
  12. if (isset($_GET['files']) && !empty($_GET['files'])) {
  13.     $files = $_GET['files'];
  14.  
  15. // exit if the list of files has not been set
  16. } else {
  17.     exit;
  18. }
  19.  
  20. // get list of requested files
  21. $files = explode(',', $files);
  22.  
  23. // set base directory of our css files
  24. $filebase = '/path/to/css/files/';
  25.  
  26. // prepare the final string of css contents
  27. $result = '';
  28.  
  29. // loop through each file
  30. foreach ($files as $file) {
  31.     // check if the file only consists or letters, underscores and dashes
  32.     if (preg_match('/[a-z_-]+/i', $file) != 0) {
  33.         // concatenate the full path to the file
  34.         $filename = $filebase . $file;
  35.  
  36.         // only fetch contents if the file exists
  37.         if (file_exists($filename)) {
  38.             // get contents of the file
  39.             $css = file_get_contents($filename);
  40.  
  41.             // compress contents of the css file
  42.             $css = compressCss($css);
  43.  
  44.             // append the compressed result to our final result
  45.             $result .= $css;
  46.         }
  47.     }
  48. }
  49.  
  50. // print compressed css
  51. print $result;

After you have created this file you can save all your css files in "/path/to/css/files" and call the compressor with something like "css.php?master,helpers,registration".

Of course this is just to tickle your fancy. The real life implementation is still your own responsibility :)

Hope this helps, enjoy!

Comments
No comments
Name
Email (required)
will not be published
Website
Recaptcha
you will only be required to fill it in once in this session

You can use [code][/code] tags in your comments