Server Fault is a question and answer site for system and network administrators. Join them; it only takes a minute:

Sign up
Here's how it works:
  1. Anybody can ask a question
  2. Anybody can answer
  3. The best answers are voted up and rise to the top

I'm using nginx reverse proxy cache with gzip enabled. However, I got some problems from Android applications HTTP-requests to my Rails JSON web service. It seems when I turn off reverse proxy cache, it works ok because the response header comes without gzip. Therefore, I think the problem is caused by gzip. What is the most appropriate level of gzip compression?

gzip               on;
gzip_http_version  1.0;
gzip_vary          on;
gzip_comp_level    6;
gzip_proxied       any;
gzip_types         text/plain text/css text/javascript application/javascript application/json application/x-javascript text/xml application/xml application/xml+rss;
share|improve this question
up vote 12 down vote accepted

The level of gzip compression simply determines how compressed the data is on a scale from 1-9, where 9 is the most compressed. The trade-off is that the most compressed data usually requires the most work to compress/decompress, so if you have it set fairly high on a high-volume website, you may feel its effect.

It sounds like your issues are more related to the HTTP headers on the requests. Usually gzip-compressed HTTP traffic is accompanied by the Content-Encoding: gzip header. If this is being dropped somewhere, then the client might not know to have to decompress the response.

share|improve this answer
How to disable gzip response using http request header from the client? I try Accept-Encoding: '', but it doesn't work. – Chamnap Mar 30 '11 at 4:01
From RFC2616 ( I think you want just 'Accept-Encoding: ' with nothing following. – growse Mar 30 '11 at 8:28
Yeah, I added the header Accept-Encoding with empty string with poster addon on mozilla, and the response back without Content-Encoding: 'gzip'. However, on the android app, it always returns back in gzip. I checked what has been cached in the proxy cache directories, nginx caches the gzip content, so it's probably responses back in gzip. How to solve this? – Chamnap Mar 30 '11 at 9:03

I tested this under nginx 1.3.9 with two files, and these were the results I got for the various levels:

text/html - phpinfo():

0    55.38 KiB (100.00% of original size)
1    11.22 KiB ( 20.26% of original size)
2    10.89 KiB ( 19.66% of original size)
3    10.60 KiB ( 19.14% of original size)
4    10.17 KiB ( 18.36% of original size)
5     9.79 KiB ( 17.68% of original size)
6     9.62 KiB ( 17.37% of original size)
7     9.50 KiB ( 17.15% of original size)
8     9.45 KiB ( 17.06% of original size)
9     9.44 KiB ( 17.05% of original size)

application/x-javascript - jQuery 1.8.3 (Uncompressed):

0    261.46 KiB (100.00% of original size)
1     95.01 KiB ( 36.34% of original size)
2     90.60 KiB ( 34.65% of original size)
3     87.16 KiB ( 33.36% of original size)
4     81.89 KiB ( 31.32% of original size)
5     79.33 KiB ( 30.34% of original size)
6     78.04 KiB ( 29.85% of original size)
7     77.85 KiB ( 29.78% of original size)
8     77.74 KiB ( 29.73% of original size)
9     77.75 KiB ( 29.74% of original size)

I'm not sure how representative this is but it should serve as an example. Also, I haven't taken the CPU usage into account but from these results the ideal compression level seems to be between 4 and 6.

Additionally, if you use the gzip_static module, you may want to pre-compress your files (in PHP):

function gzip_static($path)
    if ((extension_loaded('zlib') === true) && (is_file($path) === true))
        $levels = array();
        $content = file_get_contents($path);

        foreach (range(1, 9) as $level)
            $levels[$level] = strlen(gzencode($content, $level));

        if ((count($levels = array_filter($levels)) > 0) && (min($levels) < strlen($content)))
            if (file_put_contents($path . '.gz', gzencode($content, array_search(min($levels), $levels)), LOCK_EX) !== false)
                return touch($path . '.gz', filemtime($path), fileatime($path));

    return false;

This allows you to get the best possible compression without sacrificing the CPU on every request.

share|improve this answer
this jibes with results at which show big drop off in compression levels after level 5 and 6. – Jeff Atwood Jul 8 '14 at 6:23

If you really can spare CPU resources, you can use 9, but for most sites a value of 2 is enough, since gzip doesn't reduce the file much after level 1.

share|improve this answer

If you have high volume website and still would like to have full level (9) of compression, best idea would be to put your static content on Amazon S3 or similar object storage services, and upload the compresses files.

You still would want to use nginx to compress your html, so better to keep that value to normal, I use 5 there.

share|improve this answer

Your Answer


By posting your answer, you agree to the privacy policy and terms of service.

Not the answer you're looking for? Browse other questions tagged or ask your own question.