PHP: Easy Javascript compression with closure compiler

Published:

Here's how to fairly easily compress/minify Javascript by using the Closure Compiler Service API.

More or less verbatim how I'm currently doing it over at bibelstudiet.no in my script controller class, and so far it's been working great. Just remember to cache the result on your server so that you're not calling the API more than necessary. In my case it's handled further up the chain by the parent class 🙂

<?php
ob_start('ob_gzhandler');
header('Content-Type: text/javascript; charset=utf-8');

// The files to compress
$files = ['foo.js', 'bar.js'];

// Input and merge them into a single string
$js = array_map('file_get_contents', $files);
$js = implode(PHP_EOL.PHP_EOL, $js);

// Setup the request
$c = curl_init();
curl_setopt_array($ch, array
(
    CURLOPT_URL => 'https://closure-compiler.appspot.com/compile',
    CURLOPT_POST => TRUE,
    CURLOPT_POSTFIELDS => http_build_query([
        'language' => 'ECMASCRIPT5',
        'output_info' => 'compiled_code',
        'output_format' => 'text',
        'compilation_level' => 'SIMPLE_OPTIMIZATIONS',
        'js_code' => $js,
    ]),
));

// Execute it, which also outputs the minified response
if(curl_exec($ch) === FALSE)
    http_response_code(500) and exit("// ERROR: ".curl_error($c));

// If the response was empty, it failed, so output the original files instead
if(curl_getinfo($ch, CURLINFO_CONTENT_LENGTH_DOWNLOAD ) <= 1)
    echo $js;

curl_close($ch);

Note that if the compilation fails for any reason, the response will be empty. In that case I've chosen to output the original Javascript instead so the site doesn't suddenly break. To check what went wrong, you need to repeat the request, but output_info set to errors instead of compiled_code.

See their API documentation for more information about the parameters.