I have nginx installed with gzip_static activated. It works fine for CSS and JavaScript files, but it also looks for gzipped versions of image files like .png and .gif, although these are not in the list of files to be compressed:
# strace -p 25044 2>&1 | grep gz
open("/var/www/css/ymax.css.gz", O_RDONLY|O_NONBLOCK) = 438
open("/var/www/images/tools.png.gz", O_RDONLY|O_NONBLOCK) = -1 ENOENT (No such file or directory)
open("/var/www/images/ads/bs.gif.gz", O_RDONLY|O_NONBLOCK) = -1 ENOENT (No such file or directory)
open("/var/www/images/gfxborder/border_right.gif.gz", O_RDONLY|O_NONBLOCK) = -1 ENOENT (No such file or directory)
open("/var/www/images/ads/hocuto03.gif.gz", O_RDONLY|O_NONBLOCK) = -1 ENOENT (No such file or directory)
Here's my nginx configuration:
gzip on;
gzip_disable "msie6";
gzip_min_length 1000;
gzip_types text/plain text/css application/x-javascript text/javascript;
gzip_static on;
Is there a way to prevent this?
I found a solution. In fact, two possible solutions:
keep javascript and CSS files in a separate directory and create "location" rule to use gzip_static only for that directory
if this is not possible (hosting multiple websites, not everything under your control, too many directories and files) there is an easier solution to prevent multiple open() calls by using open_file_cache_errors setting which caches (i.e remembers) that .gz file was not present and does not try to open it again.
I found a way to edit the source code of nginx but in a very awful way :
- find file :
ngx_http_gzip_static_module.c (ver 1.0.1, other version may be the same):
2 .in:
ngx_http_gzip_static_handler(ngx_http_request_t *r)
3 .found :
if (r->uri.data[r->uri.len - 1] == '/') {
return NGX_DECLINED;
}
- add :
if ( r->uri.data[r->uri.len - 1] == 'g' && r->uri.data[r->uri.len - 2] == 'n' && r->uri.data[r->uri.len - 3] == 'p' && r->uri.data[r->uri.len - 4] == '.') {
return NGX_DECLINED;
}
if ( r->uri.data[r->uri.len - 1] == 'g' && r->uri.data[r->uri.len - 2] == 'p' && r->uri.data[r->uri.len - 3] == 'j' && r->uri.data[r->uri.len - 4] == '.') {
return NGX_DECLINED;
}
if ( r->uri.data[r->uri.len - 1] == 'o' && r->uri.data[r->uri.len - 2] == 'c' && r->uri.data[r->uri.len - 3] == 'i' && r->uri.data[r->uri.len - 4] == '.') {
return NGX_DECLINED;
}
- Recompile your source.
Anyone know C can edit it to be more professtinal because I don't know C :(
I have discovered a simple way of doing this using nested location blocks:
location /assets {
root /usr/share/nginx/html;
location ~ .*.(js|css|html|png)+$ {
# Use for debugging
# add_header 'X-static-gzipping' 'on' always;
gzip_static on;
}
}