Короткий ответ: gzip в nginx включается тремя директивами — gzip on, gzip_types со списком типов и gzip_min_length, ниже которого сжимать невыгодно. Brotli даёт на тексте на 15–25 % меньше объёма, но его модуль не входит в стандартную сборку nginx и требует отдельной установки. Включать оба сразу можно: nginx отдаст brotli клиентам, которые его поддерживают, и gzip остальным.
Это часть работ по разработке и поддержке сайтов; смежная тема — установка и настройка nginx.
Зачем сжимать
HTML, CSS, JavaScript, JSON и SVG — текстовые форматы с высокой избыточностью. Сжатие уменьшает их в 3–10 раз. На медленном мобильном соединении это прямо влияет на время загрузки, а оно учитывается и в поисковых системах, и в конверсии.
| Тип файла | Сжимать | Почему |
|---|---|---|
| HTML, CSS, JS, JSON, XML | Да | Текст, высокая избыточность |
| SVG | Да | Это XML внутри |
| JPEG, PNG, WebP, AVIF | Нет | Уже сжаты, эффекта не будет, только расход процессора |
| WOFF2 | Нет | Внутри уже применено сжатие |
| MP4, MP3 | Нет | Уже сжаты |
Включение gzip для картинок — распространённая ошибка: трафик не уменьшается, а нагрузка на процессор растёт на каждом запросе.
Настройка gzip
Директивы размещаются в блоке http или в конкретном server:
gzip on;
gzip_vary on;
gzip_proxied any;
gzip_comp_level 5;
gzip_min_length 1024;
gzip_types
text/plain
text/css
text/xml
text/javascript
application/javascript
application/json
application/xml
application/rss+xml
image/svg+xml;
# отключить сжатие для старых версий IE
gzip_disable "msie6";
| Директива | Смысл |
|---|---|
gzip_vary on |
Добавляет заголовок Vary: Accept-Encoding — без него кэши могут отдать сжатый ответ клиенту, который его не понимает |
gzip_proxied any |
Сжимать и ответы для прокси и CDN; без этого сжатие может не применяться за Cloudflare |
gzip_comp_level 5 |
Разумный компромисс: уровни 1–9 дают убывающую прибавку при растущем расходе процессора |
gzip_min_length 1024 |
Файлы меньше килобайта сжимать невыгодно — заголовки съедят выигрыш |
Уровень сжатия выше 6 почти не уменьшает размер, но заметно нагружает процессор. На сервере, который отдаёт много статики, разница между 5 и 9 ощутима по нагрузке и незаметна по трафику.
Brotli
Brotli даёт меньший размер, чем gzip, особенно на JavaScript и CSS. Модуль ngx_brotli не входит в стандартную сборку — его нужно устанавливать отдельно, а для этого часто пересобирать nginx. В репозиториях Debian и Ubuntu готового пакета обычно нет.
Если модуль подключён, настройка выглядит так:
brotli on;
brotli_comp_level 5;
brotli_static on;
brotli_types
text/plain
text/css
text/xml
text/javascript
application/javascript
application/json
application/xml
image/svg+xml;
Директива brotli_static on позволяет отдавать заранее подготовленные файлы .br, если они лежат рядом с оригиналом — тогда сжатие не тратит процессорное время вообще.
Проверка
Заголовок Content-Encoding в ответе показывает, применено ли сжатие:
# gzip
curl -s -H "Accept-Encoding: gzip" -I https://example.com/ | grep -i content-encoding
# brotli
curl -s -H "Accept-Encoding: br" -I https://example.com/ | grep -i content-encoding
# размер до и после
curl -s -o /dev/null -w "без сжатия: %{size_download} байтn" https://example.com/
curl -s -H "Accept-Encoding: gzip" -o /dev/null -w "gzip: %{size_download} байтn" https://example.com/
Если Content-Encoding не появляется, проверяйте в таком порядке: тип содержимого входит в gzip_types, размер больше gzip_min_length, ответ не отдаётся из кэша без заголовка Vary.
Кэширование статики
Сжатие работает вместе с кэшированием. Сжатый ответ выгодно кэшировать, чтобы не тратить процессор повторно:
location ~* .(css|js|svg|woff2)$ {
expires 1y;
add_header Cache-Control "public, immutable";
access_log off;
}
location ~* .(jpg|jpeg|png|webp|avif|gif|ico)$ {
expires 1y;
add_header Cache-Control "public, immutable";
access_log off;
}
Долгий срок хранения требует «отпечатка» в имени файла: при изменении содержимого меняется имя, и клиент забирает новую версию. Без этого посетители будут месяцами получать старый файл из кэша.
Что проверять после включения
nginx -t— синтаксис конфигурации.systemctl reload nginx— применение без разрыва соединений.- Проверка
Content-Encodingдля HTML, CSS и JS отдельно. - Сравнение размера ответа до и после.
- Загрузка процессора после включения — на слабом сервере высокий уровень сжатия заметен.
- Проверка, что картинки и шрифты не попали в сжатие.
Отдельно стоит проверить сайт под нагрузкой: сжатие на каждый запрос — это работа процессора, и на сервере с одним ядром при большом трафике эффект может оказаться отрицательным. В таких случаях помогает gzip_static on с заранее подготовленными файлами.
