Серверное кэширование — это одно из самых действенных средств оптимизации нагрузки в веб‑приложениях. Angie предоставляет широкие возможности настройки, с помощью которых можно реализовать множество сценариев использования кэша.
Навигация по циклу
Настройка location в Angie. Разделение динамических и статических запросов
Перенаправления в Angie: return, rewrite и примеры их применения
Сжатие текста в Angie: статика, динамика, производительность
Серверное кэширование в Angie: тонкости настройки
Видеоверсия
Для вашего удобства подготовлена видеоверсия этой статьи, доступна на Rutube, VKVideo и YouTube.
Принцип работы кэша в Angie
Сразу стоит оговориться, что в этой статье мы рассматриваем серверное кэширование ответов бэкенда с помощью модуля http_proxy. Аналогичные настройки есть в других модулях проксирования (fastcgi, scgi, uwsgi
). Основная цель такого кэширования — сохранить ответ бэкенда и использовать его при повторных запросах клиентом того же ресурса. Кэш в Angie хранится на диске, при этом каждый элемент представляет собой файл. Путь к файлу и его имя определяются настройками зоны и ключа кэширования.
Здесь может возникнуть закономерный вопрос: почему не разместить кэш в оперативной памяти? Действительно, доступ к элементам кэша в памяти будет быстрее, но есть два аргумента против хранения кэша в RAM. Во‑первых, часто используемые файлы в большинстве операционных систем и так кэшируются при наличии свободной памяти, поэтому доступ к ним будет таким же быстрым. Во‑вторых, наличие кэша на диске даёт возможность быстрого старта без длительной фазы «прогрева» сервера. Ну и конечно, места на диске гораздо больше и можно значительно увеличить размер кэша.
Каждый элемент кэша имеет время актуальности и срок хранения на диске. Начальной загрузкой и удалением файлов управляют специальные процессы: cache loader
и cache_manager
соответственно.
Первое, что нужно настроить для использования серверного кэша — это зона кэширования.
Настройка зоны кэширования
Хранение кэша в Angie распределено по зонам. Каждая зона — это каталог внутри файловой системы, задаётся зона директивой proxy_cache_path
. Разберём пример конфигурации зоны кэша:
http {
proxy_cache_path /var/www/cache levels=1:2 keys_zone=one:10m:file=/etc/angie/cache.state inactive=4h max_size=800m;
}
Первый параметр — это путь для хранения файлов кэша (/var/www/cache
). Далее мы указываем количество уровней вложенности для разбиения файлов по директориям, максимально можно указать до трёх уровней вложенности. В каждом уровне можно указать 1 или 2 — это количество цифр в названии директории. Например при наших настройках файл кэша с именем 582f017bcde4b1e41623812ee6d93350
будет расположен в директории: /var/www/cache/0/35
.
В параметре keys_zone
задаётся название зоны (one
), размер области разделяемой памяти для хранения ключей (10m
), а также файл (cache.state
) для хранения состояния ключей при перезагрузке процесса и последующего восстановления их в памяти. Хранение статуса кэша в файле появилось в Angie 1.9.0.
Следующий параметр (inactive
) указывает, как долго хранить файлы кэша, если к ним не было обращений (4 часа). Наконец, задаём максимальный размер кэша (max_size
) на диске (800 МБ). Также можно задать параметр минимально доступного сводного пространства на файловой системе с кэшем (min_free
).
Для более тонкой настройки процессов загрузки и очистки кэша по нагрузке на диск можно использовать директивы manager/loader_files
, manager/loader_threshold
, manager/loader_sleep
.
Настроив зону кэширования, можно переходить к настройке ключа кэширования.
Настройка ключа кэширования
Важнейшим аспектом настройки будет определение ключа кэширования. Это набор переменных, которые являются аргументом хэш‑функции для определения имени файла кэша. Одним из логичных вариантов может быть следующий вариант:
proxy_cache_key $scheme$host$uri;
В этой настройке ответ определяется по его полному адресу (схема, хост, URI без параметров). Если содержимое ответа зависит от других параметров запроса (заголовки, значения cookie и т. д.), достаточно добавить их в ключ. Например, добавим значение cookie с названием ID:
proxy_cache_key $scheme$host$uri$cookie_ID;
От значения ключа будет рассчитан MD5-хеш, который будет определять название файла и его размещение в зоне кэширования. Теперь мы готовы активировать кэш, то есть включить его в location с проксированием.
Подключение кэша в location
Логично подключать кэш в location
, который проксируется на бэкенд. Основная директива, которая включает кэш — это proxy_cache
. Но как правило мы хотим более тонко контролировать поведение кэша и типичная конфигурация будет выглядеть примерно так:
server {
location / {
proxy_cache one;
proxy_cache_valid 200 10s;
proxy_cache_lock on;
proxy_cache_background_update on;
proxy_cache_use_stale updating;
proxy_pass http://backend;
}
}
Первая директива (proxy_cache
) включает использование кэша с зоной one. Далее мы устанавливаем на уровне location время валидности (proxy_cache_valid
) ответа в кэше и указываем кэшировать ответы с кодом 200 на 10 секунд. Можно указывать несколько директив proxy_cache_valid
для различных кодов ответа. Также для работы кэширования обязательно должна быть включена буферизация ответа (proxy_buffering
), что является значением по умолчанию.
Время кэширования определяется особенностями контента. Для редких изменений подходит большое время валидности кэша, а для динамического контента подходит минимальное время. Например, при нагрузке в 100 RPS кэширование на одну секунду даёт снижение нагрузки на бэкенд примерно в 100 раз.
Для оптимизации производительности включена блокировка при записи в кэш (proxy_cache_lock
), что обеспечивает только один запрос к бэкенду для обновления элемента кэша, даже если есть несколько параллельных запросов от клиентов к данному ресурсу. Кроме того, включён режим фонового обновления кэша (proxy_cache_background_update
), при котором клиенту быстро отдаётся устаревший ответ, а в это время происходит обновление кэша. Чтобы фоновое обновление кэша работало, необходима следующая директива (proxy_cache_use_stale
), которая разрешает отдавать устаревший ответ из кэша.
На этом настройку кэширования можно считать законченной, но есть еще несколько важных аспектов, которые стоит рассмотреть. Начнём с обхода кэша и запроса кэширования определённых ответов.
Обход и запрет кэша
Типичной задачей при работе с кэшем является получение гарантированно свежего ответа, минуя кэш. Для этого существует директива proxy_cache_bypass
. Например:
proxy_cache_bypass $cookie_forceupdate $arg_forceupdate;
При такой настройке достаточно установить cookie c названием forceupdate с непустым значением или добавить в запрос GET‑параметр forceupdate. Например: http://test/test?forceupdate=1
.
Также важно понимать, что Angie использует заголовки ответа для принятия решения о кэшировании. То есть бэкенд может задать заголовки Cache‑Control, Expires, X‑Accel‑Expires
и через них управлять кэшированием. Также не кэшируются ответы с заголовком Set‑Cookie
и Vary «*»
. Обработку этих заголовков можно отключить с помощью директивы proxy_ignore_headers
:
proxy_ignore_headers "X-Accel-Expires" "Expires" "Cache-Control";
С такой конфигурацией ответы будут кэшироваться даже при наличии заголовков, запрещающих сохранение в кэше. То есть, клиенты могут получать устаревшие ответы даже, если приложение явно запрещает их кэширование.
Полностью запретить кэширование определённых ответов можно с помощью директивы proxy_no_cache
, которая настраивается по аналогии с proxy_cache_bypass
:
proxy_no_cache $cookie_nocache $arg_nocache$arg_comment;
В конфигурации выше запрещается кэшировать ответы при наличии cookie с именем nocache или при наличии параметров nocache или comment.
Ограничить кэш можно и по HTTP‑методам запроса, по умолчанию кэшируются GET и HEAD‑запросы, но можно расширить или сократить список методов, например:
proxy_cache_methods GET HEAD POST;
Таким образом, у нас существует широкий выбор средств тонкой настройки объектов кэширования. В Angie существует возможность использовать кэш в случае отказа бэкенда, рассмотрим такой вариант подробнее.
Обработка ошибок бэкенда
Допустим, бэкенд (или вся группа серверов) на момент запроса недоступны (нет подключения, 5xx ошибки и т.д.), но в кэше уже есть ответ (пусть и устаревший). Скорее всего, лучше отдать старый ответ, пока поднимаются бэкенды, чем ответить ошибкой пользователю. Настроить такое поведение можно с помощью директивы proxy_cache_use_stale
, например с такими параметрами:
proxy_cache_use_stale updating error timeout invalid_header http_500 http_502 http_504;
Здесь довольно широкие полномочия по использованию устаревшего ответа из кэша: во время обновления кэша, при ошибке выбора сервера, при таймаутах по работе с сервером, при ошибках с ответом, при кодах ответа 500, 502 и 504.
Использование такого механизма нужно учитывать при настройке мониторинга приложения через запросы на Angie, так как падение бэкенда может быть замаскировано кэшированными ответами.
Кэширование больших ответов
При работе с ответами большого размера (видео, архивы) полезно использовать модуль Slice, который умеет делить ответ на диапазоны. Дело в том, что при обычном алгоритме работы ответ будет помещен в кэш только после полного получения на стороне Angie. Далее ответ будет целиком размещён в одном файле на диске. То есть, получаем высокие задержки при записи кэша на диск и при обращении к нему.
Решение состоит в разделении ответа (slice
), при этом кэширование начинает работать с частями ответа, что позволяет более гибко и эффективно применять кэш.
Конфигурация кэша с разделением представлена ниже.
location /video {
slice 10m;
proxy_cache cache_slice;
proxy_cache_key $host$uri$slice_range;
proxy_set_header Range $slice_range;
proxy_cache_valid 200 206 1h;
proxy_pass http://backend;
}
В этом примере задействовано разделение ответа на части по 10 МБ (slice 10m
). Для корректной работы в ключ кэширования добавлена переменная $slice_range
, а также заголовок Range
. Теперь необходимо добавить кэширование ответов (proxy_cache_valid
) с кодом 206 (Partial Content). На этом кэширование с разделением ответа настроено.
Точечная очистка кэша
Стандартный механизм кэширования не поддерживает точечную очистку элементов кэша средствами Angie. Но задачу можно решить сторонним модулем Cache Purge. Необходимо его установить и подключить в главную секцию конфига angie.conf:
apt install angie-module-cache-purge
load_module modules/ngx_http_cache_purge_module.so;
Теперь мы можем настроить сброс кэша по специальному запросу. Простейшая конфигурация для использования одного location выглядит так:
server {
location / {
proxy_cache one;
proxy_pass http://backend;
proxy_cache_purge PURGE from 127.0.0.1;
}
}
Здесь мы добавили возможность сброса кэша при запросе только с localhost. Запрос можно сформировать следующей командой:
curl -X PURGE http://127.1/*
Показанный выше запрос имеет метод PURGE
для сброса кэша и будет очищать кэш по маске для URI /* (частичный ключ), причём звёздочку можно ставить только в конце. Важно, чтобы запрос на очистку по значению ключа совпадал с ключом кэша. В ответе можно увидеть успешный или неуспешный статус очистки и значения ключа, которые были очищены. Для корректной работы удаления кэша по маске последним параметром ключа кэширования должна быть переменная $uri
.
Другой вариант настройки — отдельный location
для очистки. То есть, запросы на очистку должны приходить на специальный адрес. При этом состав ключа для поиска удаляемых элементов указывается в директиве proxy_cache_purge
. Пример показан ниже.
http {
map $uri $wpurgeuri {
"~/purge(?<wpurge>/.*)" $wpurge;
default $uri;
}
server {
location / {
proxy_cache one;
proxy_pass http://backend;
proxy_cache_purge PURGE from 127.0.0.1;
}
location /purge {
allow 127.0.0.1;
deny all;
proxy_cache_purge one $wpurgeuri$is_args$args;
}
}
}
Здесь создаётся специальная переменная $wpurgeuri
, которая будет служить ключом для очистки кэша, она формируется из $uri
, но без префикса /purge
.
Для такой конфигурации запрос на очистку кэша должен включать префикс /purge
, например:
curl -X PURGE http://127.1/purge/*
Таким образом, мы получаем возможность частичной очистки кэша.
Логирование и мониторинг
Статистику по кэшу можно наблюдать по API или с помощью Angie Console Light. Также в Angie встроен экспортер для Prometheus для последующей визуализации в Grafana. Доступен процент попадания в кэш, его статус, объём файлов на диске, статистика по трафику и заполнение зоны разделяемой памяти.

Статус кэширования полезно фиксировать в логах. Для этого доступна переменная $upstream_cache_status
.
Итоги
Надеюсь, теперь у вас сложилось общее впечатление о возможностях серверного кэширования в Angie. При грамотном использовании кэш может радикально снизить время ответа приложения и разгрузить серверные мощности на бэкенде. Мы рассмотрели большинство аспектов настройки, а также решили типичные задачи. В завершение научились точечно очищать кэш с помощью стороннего модуля и поговорили о мониторинге кэша.
Комментарии (5)
Zeroxzed
21.07.2025 19:25Отличный материал. Коротко, всё по делу. Насколько я понял, для Nginx все настройки будут аналогичные? Не увидел, чтобы здесь использовалось что-то специфичное именно для Angie.
Nickmob Автор
21.07.2025 19:25Не совсем. Например, в Nginx нет файла для сохранения состояния кэша в proxy_cache_path. В Nginx есть дополнительные опции в Nginx Plus, в общем, нужно смотреть.
VBart
21.07.2025 19:25Добавлю ещё, что мониторинга состояния кэша в open source версии nginx тоже никакого нет.
pae174
Кому такое надо, те просто делают диск в оперативной памяти и хранят кэш там.