Три разных продукта: nginx, Angie, OpenResty - и зачем они нужны
Все трое - это веб-серверы и обратные прокси на общем коде, но решают разные задачи, и путать их нельзя.
nginx - оригинал, теперь под крылом F5. Это база, эталон, на нём построены оба остальных. В 2026 году актуальны две ветки: stable 1.30.x (на момент написания 1.30.2) и mainline 1.31.x (1.31.1). Это важно зафиксировать в голове: никаких 1.27 и 1.25 - они устарели. Отдельно держи в уме freenginx - форк Максима Дунаева, одного из ключевых разработчиков nginx; он живой, выпускает свои security-релизы (stable 1.30.1, mainline 1.31.2) и не заброшен. Для большинства задач ты ставишь именно nginx с nginx.org.
Angie - форк nginx от части бывшей команды, который бесплатно и нативно даёт то, за что в nginx исторически просили деньги или городили костыли: активные health checks для апстримов, slow_start, детальный REST API /status с JSON по зонам и апстримам, метрики Prometheus, нативный ACME прямо в конфиге (выпуск сертификатов без certbot), нативный Zstd-сжатие, динамическое управление апстримами через API без reload, автообнаружение контейнеров по меткам Docker. Версии 2026 - около 1.11.6 (база nginx 1.29.x) и ветка 1.12 (база 1.31.1). Если тебе нужен зрелый шлюз с мониторингом из коробки - смотри на Angie.
OpenResty - это nginx, в который встроили LuaJIT (свой форк openresty/luajit2 с GC64) и десятки Lua-модулей. Превращает сервер в программируемую платформу: ты пишешь логику обработки запроса прямо на Lua внутри конфига. Версия 2026 - 1.31.1.1 (вышла 5 июня 2026). Именно на OpenResty строят полноценные API-gateway, к чему мы и придём в конце курса. Эталонный проект нашего курса - ngx-trace-gateway - крутится как раз на образе openresty/openresty.

Установить nginx: дистрибутивный пакет против официального репозитория
Когда ты делаешь установку nginx через apt из штатных репозиториев Ubuntu или Debian, ты получаешь версию, которую заморозил мейнтейнер дистрибутива. Это удобно (одна команда, автообновления с системой), но версия старая. На свежей Ubuntu это может быть 1.28.x или старше - без части модулей и фич 2026 года. Для теста сойдёт, для прода - почти всегда нет.
Профессиональный путь - официальный репозиторий nginx.org. Там и stable, и mainline, всегда свежие. Вот полная nginx установка ubuntu/debian из официального источника:
Код: Выделить всё
# зависимости
sudo apt update
sudo apt install -y curl gnupg2 ca-certificates lsb-release debian-archive-keyring
# импортируем ключ подписи в отдельный keyring (так правильно в 2026, не apt-key)
curl https://nginx.org/keys/nginx_signing.key | gpg --dearmor \
| sudo tee /usr/share/keyrings/nginx-archive-keyring.gpg >/dev/null
# подключаем STABLE-ветку (для Debian замени ubuntu на debian)
echo "deb [signed-by=/usr/share/keyrings/nginx-archive-keyring.gpg] \
http://nginx.org/packages/ubuntu $(lsb_release -cs) nginx" \
| sudo tee /etc/apt/sources.list.d/nginx.list
# для MAINLINE - вместо packages/ubuntu пиши packages/mainline/ubuntu
# пиннинг: чтобы пакет тянулся именно с nginx.org, а не из дистрибутива
echo -e "Package: *\nPin: origin nginx.org\nPin: release o=nginx\nPin-Priority: 900\n" \
| sudo tee /etc/apt/preferences.d/99nginx
sudo apt update
sudo apt install -y nginx
На RHEL-семействе (RHEL, Rocky, Alma, Fedora) - через dnf и .repo-файл:
Код: Выделить всё
# /etc/yum.repos.d/nginx.repo
[nginx-stable]
name=nginx stable repo
baseurl=http://nginx.org/packages/centos/$releasever/$basearch/
gpgcheck=1
enabled=1
gpgkey=https://nginx.org/keys/nginx.org.key
module_hotfixes=true
# затем
sudo dnf install -y nginx
Установка Angie и OpenResty: отдельные репозитории
Angie ставится из своего репозитория - схема та же, но домен и ключ другие. Принцип: добавляешь репозиторий angie.software, импортируешь их ключ, ставишь пакет angie. Базовый пакет даёт ядро, а вот фичи вроде /status-консоли и Prometheus уже встроены в основной бинарник - доплачивать или докачивать сторонние модули не нужно, в этом и фишка. Проверь установку так же, как nginx: angie -v и angie -V (бинарник называется angie, но конфиг-синтаксис совместим с nginx, и многие зовут его через симлинк).
OpenResty установка - тоже отдельный репозиторий, бинарник лежит в /usr/local/openresty/ и называется openresty (это обёртка над nginx с вкомпилированным LuaJIT):
Код: Выделить всё
# Debian/Ubuntu, кратко
curl -fsSL https://openresty.org/package/pubkey.gpg | sudo gpg --dearmor \
-o /usr/share/keyrings/openresty.gpg
echo "deb [signed-by=/usr/share/keyrings/openresty.gpg] \
http://openresty.org/package/ubuntu $(lsb_release -cs) main" \
| sudo tee /etc/apt/sources.list.d/openresty.list
sudo apt update && sudo apt install -y openresty
# проверка - в выводе должно быть LuaJIT
openresty -V
# nginx version: openresty/1.31.1.1
# built with OpenSSL ...
# --with-luajit ... --with-http_ssl_module ...
nginx docker: образы, которые экономят часы
Для контейнерных стендов и CI ничего ставить руками не надо. nginx docker - это официальные образы с Docker Hub. Три семейства, которые надо знать:
- nginx - официальный образ. Теги nginx:1.30 (stable), nginx:1.31 (mainline), nginx:latest, плюс лёгкие nginx:1.30-alpine на musl-базе (меньше размер).
- openresty/openresty - образ OpenResty с LuaJIT и Lua-модулями. На нём построен наш эталонный ngx-trace-gateway.
- -otel образы - сборки с официальным модулем телеметрии ngx_otel_module внутри. Важно: этот модуль open-source (не Plus-only), доступен с nginx 1.25.3, а с 1.27.5 включён в -otel-образы по умолчанию. Даёт распределённую трассировку через OTLP/gRPC с W3C trace context.
Код: Выделить всё
# поднять nginx stable, прокинуть свой конфиг только на чтение (ro)
docker run -d --name gw \
-p 80:80 \
-v $(pwd)/nginx.conf:/etc/nginx/nginx.conf:ro \
nginx:1.30
# проверить версию и флаги сборки внутри контейнера
docker exec gw nginx -V
# проверить синтаксис конфига (это же делает healthcheck в эталонном проекте)
docker exec gw nginx -t
nginx -V: как прочитать паспорт своего бинарника
Это самая важная диагностическая команда курса. nginx -v (маленькая) показывает только версию. А nginx -V (большая) - это паспорт: версия, компилятор, версия OpenSSL и полный список флагов ./configure, с которыми бинарник собран. Именно отсюда ты узнаёшь, что твой nginx умеет:
Код: Выделить всё
nginx -V
# nginx version: nginx/1.30.2
# built by gcc ...
# built with OpenSSL 3.5.0 ...
# TLS SNI support enabled
# configure arguments: --with-http_ssl_module --with-http_v2_module
# --with-http_v3_module --with-http_realip_module
# --with-http_stub_status_module --with-stream ...
- Нет --with-http_v3_module - HTTP/3 и QUIC просто не заработают, хоть ты обпишись listen 443 quic. Надо ставить сборку с поддержкой v3.
- Версия OpenSSL критична: пост-квантовый обмен ключей (ssl_ecdh_curve X25519MLKEM768) требует OpenSSL 3.5+; в nginx 1.29.8 завезли поддержку OpenSSL 4.0. Старый OpenSSL - нет гибридного TLS, и Chrome с Firefox не дадут тебе пост-квантовый хендшейк.
- Нет --with-http_realip_module - и тогда $remote_addr у тебя будет адресом ближайшего прокси или CDN, а не клиента. Это ломает логи, rate-limit и geo. Модуль realip обязателен за любым балансировщиком.
- --with-stream - нужен для проксирования TCP/UDP (L4), а не только HTTP.
Структура файлов и systemd
После пакетной установки конфиги лежат в /etc/nginx. Раскладка:
- /etc/nginx/nginx.conf - главный файл, точка входа. В эталонном проекте он минимален: worker_processes auto, error_log, pcre_jit on, и include на events.conf и http.conf.
- /etc/nginx/conf.d/*.conf - сюда официальный пакет nginx.org кладёт default.conf; всё, что подключено через include conf.d/*.conf, грузится автоматически.
- sites-available + sites-enabled - это схема Debian/Ubuntu, а не самого nginx. Конфиги сайтов лежат в sites-available, а в sites-enabled - симлинки на активные. Включить сайт = сделать симлинк, выключить = удалить симлинк, без правки файла. На сборках с nginx.org этой схемы по умолчанию нет - там conf.d. Не путай два подхода.
- /var/log/nginx/ - access и error логи; /usr/share/nginx/html/ - дефолтный корень сайта.
Код: Выделить всё
sudo systemctl enable --now nginx # включить в автозапуск и стартовать
sudo systemctl status nginx # состояние
sudo nginx -t # проверить конфиг ПЕРЕД релоадом
sudo systemctl reload nginx # мягко перечитать конфиг (без обрыва соединений)
sudo systemctl restart nginx # жёсткий перезапуск (соединения рвутся)
Сборка из исходников: когда ./configure неизбежен
Пакеты закрывают 95% случаев. Но иногда нужен модуль, которого нет в готовой сборке: сторонний Brotli (ngx_brotli не встроен в nginx, это сторонний динамический модуль), или специфичный апстрим-модуль. Тогда - сборка:
Код: Выделить всё
./configure --prefix=/etc/nginx \
--with-http_ssl_module --with-http_v2_module --with-http_v3_module \
--with-http_realip_module --with-stream \
--add-dynamic-module=../ngx_brotli
make && sudo make install
# модуль подключается в nginx.conf:
# load_module modules/ngx_brotli_filter_module.so;
Типичные грабли
- Поставил из дистрибутива, ждёшь фич 2026. http2 on вместо устаревшего listen ... http2, 103 Early Hints, sticky-сессии - это новое. На старом дистрибутивном nginx их нет. Проверь версию через nginx -v, прежде чем гуглить "почему не работает".
- Забыл пиннинг. Без /etc/apt/preferences.d/99nginx очередной apt upgrade молча подменит твою сборку с nginx.org на дистрибутивную. Версия откатится - сюрприз в проде.
- Меняешь конфиг в работающем контейнере. Образ собран так, что правильный путь - монтировать конфиг томом и пересоздавать контейнер, а не лезть внутрь. Том на :ro защищает от случайной правки.
- Не смотришь nginx -V. Полдня настраиваешь HTTP/3, а модуля --with-http_v3_module в сборке нет. Минута на nginx -V сэкономила бы полдня.
- Перепутал sites-enabled и conf.d. Положил конфиг в sites-available на сборке с nginx.org, где include идёт только на conf.d/*.conf - и сайт не подхватился. Проверь, какие include реально прописаны в твоём nginx.conf.
Сделай руками по шагам, это закрепит всё выше:
- 1. Подними официальный nginx stable в Docker: docker run -d --name n1 -p 8081:80 nginx:1.30. Открой http://localhost:8081 - увидишь страницу-приветствие.
- 2. Выполни docker exec n1 nginx -V и выпиши: версию, версию OpenSSL, есть ли --with-http_v3_module и --with-http_realip_module.
- 3. Подними OpenResty: docker run -d --name o1 -p 8082:80 openresty/openresty:latest. Сделай docker exec o1 openresty -V и найди в выводе --with-luajit - это маркер, что Lua-фазы доступны.
- 4. Сломай конфиг намеренно: зайди docker exec -it n1 sh, допиши в /etc/nginx/conf.d/default.conf строку мусора, выполни nginx -t - получишь ошибку с номером строки. Убери мусор, nginx -t снова - syntax is ok. Так ты увидел, почему healthcheck в эталонном проекте - это именно nginx -t.
- 5. Сравни вывод nginx -V из nginx:1.30 и nginx:1.31 - найди отличия в наборе флагов и версии. Зафиксируй для себя, что бинарники реально разные.
- 1. Чем nginx -v отличается от nginx -V и какие три вещи ты узнаёшь именно из nginx -V?
- 2. Какая ветка stable, а какая mainline на 2026 год, и почему дистрибутивный пакет - часто не лучший выбор для прода?
- 3. Зачем нужен файл пиннинга 99nginx и что произойдёт без него после apt upgrade?
- 4. Какие три возможности Angie даёт бесплатно и нативно, а в nginx их пришлось бы докупать или городить руками?
Ты научился осознанно выбирать между nginx, Angie и OpenResty, ставить любой из них из официального репозитория на Debian и RHEL, запускать в Docker с правильными паттернами (том на :ro, healthcheck через nginx -t) и - главное - читать паспорт бинарника через nginx -V, чтобы знать его реальные возможности до того, как полдня воюешь с конфигом. Зафиксируй на 2026: stable 1.30.x, mainline 1.31.x, OpenResty 1.31.1.1, Angie 1.11/1.12. Дальше мы напишем первый рабочий конфиг и разберём, как именно nginx маршрутизирует запрос между server и location.