Налаштування розподілу навантаження L4/L7 на Nginx під ключ

Коли сервери перевантажені нерівномірно, а частина запитів іде в таймаут, бізнес втрачає клієнтів і гроші. Ми налаштовуємо L4/L7 балансування на Nginx під ключ, щоб розподіляти навантаження з урахуванням потужності кожного вузла та перевірок доступності. Наша команда бере на себе весь цикл — від аудиту до впровадження та подальшої підтримки, забезпечуючи стабільну роботу вашого сервісу.
Часті запитання

Практичні сценарії налаштування Nginx для L4/L7

Уявіть: ваш інтернет-магазин гальмує, половина запитів іде в таймаут, а моніторинг показує, що один сервер перевантажений на 90%, а два інших простоюють. Це класична проблема невірно налаштованого балансування. Типова картина: backend-сервери мають різну потужність (наприклад, один з 4 vCPU, два з 2 vCPU), і round-robin направляє рівну кількість запитів, перевантажуючи слабкі вузли. Це призводить до каскадного збільшення затримки — час відповіді TTFB злітає до 3-5 секунд, а частина запитів падає через обмеження з'єднань. Промислова L7 балансування на Nginx з використанням least_connections і ваг вирішує проблему.

На практиці ми стикалися з проектом, де через round-robin час відповіді сягав 10 секунд. Після переходу на least_conn з вагами навантаження вирівнялося, а час відповіді знизився на 40%. За нашими вимірами, least_connections працює в 2-3 рази ефективніше за round-robin при різній тривалості запитів. При середньому чеку 3000 гривень втрата кожного десятого клієнта обходиться в 900 000 гривень на рік.

У цій статті розповімо про реальні технічні складнощі, які зустрічаються на практиці — від втрати сесій до SSL passthrough — і як їх подолати.

Чому балансування L4/L7 критичне для високонавантажених проектів?

Відмова одного сервера може призвести до недоступності всього сервісу. Без коректних health checks і failover користувачі отримують помилки 502. Крім того, неоптимальний розподіл запитів збільшує час відгуку в 2-3 рази, що прямо впливає на конверсію. Балансування на рівні L4 (TCP/UDP) підходить для будь-яких протоколів, але не враховує вміст запиту. L7 (HTTP/HTTPS) дає гнучкість: можна маршрутизувати за URL, заголовками, cookies. Разом вони покривають будь-які сценарії.

Коли використовувати L4, а коли L7?

Вибір рівня залежить від задачі. L4 балансування (через модуль stream) незамінне для сервісів, де не потрібно аналізувати протокол: бази даних (MySQL, PostgreSQL), Redis, SSH. Воно вносить мінімальну затримку (близько 1 мс). L7 підходить для HTTP-застосунків, де потрібні sticky sessions, канарковий деплой або A/B тестування. Наприклад, для інтернет-магазину з кошиком — L7 з IP hash або cookie-based sticky. Для мікросервісної архітектури часто комбінують: L4 для балансування трафіку між подами, L7 для маршрутизації всередині.

Проблеми, які ми вирішуємо

  • Нерівномірний розподіл навантаження. Round-robin не завжди рівномірний: при нерівномірному навантаженні на запити (наприклад, одні запити важчі за інші) сервери забиваються нерівномірно. Ми використовуємо least_connections або weighted least_connections, щоб це компенсувати.
  • Втрата сесій при збої backend. Без sticky sessions користувач знову потрапляє на інший сервер, втрачаючи дані кошика. Ми впроваджуємо cookie-based sticky або hash $cookie_SERVERID consistent.
  • Некоректні health checks. Якщо пасивна перевірка не спрацьовує, трафік іде на сервер, що впав. Налаштовуємо max_fails і fail_timeout, а для критичних систем — активні health checks через Nginx Plus або зовнішній моніторинг.
  • SSL passthrough для L4. Проксування HTTPS без розшифровки вимагає ssl_preread + SNI маршрутизацію. Це неочевидне налаштування, яке часто упускають.

Як ми це робимо: стек і конфігурація

Використовуємо Nginx Open Source (стабільна версія) або Nginx Plus при необхідності enterprise-функцій. У проектах застосовуємо GitOps-підхід: конфіги зберігаються в Git, деплой через Ansible або Terraform. Нижче — приклад робочої конфігурації для типового проекту інтернет-магазину.

L7 HTTP балансування

# /etc/nginx/conf.d/upstream.conf
upstream app_rr {
    server 10.0.1.10:8080;
    server 10.0.1.11:8080;
    server 10.0.1.12:8080;
    keepalive 64;
}

upstream app_lc {
    least_conn;
    server 10.0.1.10:8080;
    server 10.0.1.11:8080 weight=2;
    server 10.0.1.12:8080;
}

upstream app_ip_hash {
    ip_hash;
    server 10.0.1.10:8080;
    server 10.0.1.11:8080;
    server 10.0.1.12:8080 down;
}

upstream app_random {
    random two least_conn;
    server 10.0.1.10:8080;
    server 10.0.1.11:8080;
    server 10.0.1.12:8080;
}

Порівняння алгоритмів балансування

Алгоритм Sticky Ваги Рівномірність Використання
Round-robin Ні Так Хороша при однакових запитах Загальний випадок
Least_connections Ні Так Відмінна при різній тривалості запитів API, WebSockets
IP hash Так Ні Середня за NAT Stateful застосунки
Random two least_conn Ні Так Краща при >2 серверів Мікросервіси

Таблиця порівняння L4 та L7 балансування

Характеристика L4 (stream) L7 (HTTP)
Рівень TCP/UDP HTTP/HTTPS
Аналіз запиту Ні (тільки порт/IP) URL, заголовки, cookies
Sticky sessions Ні (тільки IP hash) Cookie-based, IP hash
Продуктивність Висока (мінімальна затримка) Нижча за рахунок розбору протоколу
Підтримувані сервіси Будь-які TCP (MySQL, Redis, SSH) HTTP-застосунки, API
Приклад налаштування stream { upstream { server ... } } upstream { server ... } location / { proxy_pass ... }

Health checks і failover

upstream app_backend {
    server 10.0.1.10:8080 max_fails=3 fail_timeout=30s;
    server 10.0.1.11:8080 max_fails=3 fail_timeout=30s;
    server 10.0.1.12:8080 backup;
    keepalive 64;
    keepalive_requests 1000;
    keepalive_time 1h;
}

server {
    listen 443 ssl http2;
    server_name app.example.com;
    ssl_certificate /etc/letsencrypt/live/app.example.com/fullchain.pem;
    ssl_certificate_key /etc/letsencrypt/live/app.example.com/privkey.pem;

    location / {
        proxy_pass http://app_backend;
        proxy_http_version 1.1;
        proxy_set_header Connection "";
        proxy_set_header Host $host;
        proxy_set_header X-Real-IP $remote_addr;
        proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
        proxy_set_header X-Forwarded-Proto $scheme;
        proxy_connect_timeout 5s;
        proxy_read_timeout 60s;
        proxy_next_upstream error timeout http_500 http_502 http_503;
        proxy_next_upstream_tries 2;
        proxy_next_upstream_timeout 10s;
    }
}

proxy_next_upstream — потужний, але небезпечний інструмент. Ми вмикаємо http_500 тільки після ретельного аналізу: якщо запит був POST і вже виконався частково, повторна відправка може дублювати операцію. Тому для ідемпотентних методів (GET, PUT) — так, для POST — з обережністю.

Cookie-based Sticky Sessions

upstream app_sticky {
    hash $cookie_SERVERID consistent;
    server 10.0.1.10:8080;
    server 10.0.1.11:8080;
    server 10.0.1.12:8080;
}

L4 TCP балансування через stream модуль

stream {
    log_format basic '$remote_addr [$time_local] ' '$protocol $status $bytes_sent $bytes_received ' '$session_time';
    access_log /var/log/nginx/stream-access.log basic;

    upstream mysql_cluster {
        least_conn;
        server 10.0.1.20:3306;
        server 10.0.1.21:3306;
        server 10.0.1.22:3306 backup;
    }

    server {
        listen 3306;
        proxy_pass mysql_cluster;
        proxy_connect_timeout 5s;
        proxy_timeout 300s;
    }

    upstream https_backends {
        server 10.0.1.10:443;
        server 10.0.1.11:443;
    }

    server {
        listen 443;
        proxy_pass https_backends;
        ssl_preread on;
    }
}

Для моніторингу upstream використовуємо stub_status + Prometheus-експортер — це дає метрики nginx_up, nginx_connections_active тощо.

Розширена конфігурація з резервуванням
upstream app_cluster {
    least_conn;
    server 10.0.1.10:8080 max_fails=5 fail_timeout=60s;
    server 10.0.1.11:8080 max_fails=5 fail_timeout=60s;
    server 10.0.1.12:8080 backup;
    keepalive 128;
}

server {
    listen 80 default_server;
    return 301 https://$host$request_uri;
}

server {
    listen 443 ssl http2;
    ssl_certificate /etc/nginx/ssl/cert.pem;
    ssl_certificate_key /etc/nginx/ssl/key.pem;

    location / {
        proxy_pass http://app_cluster;
        proxy_http_version 1.1;
        proxy_set_header Upgrade $http_upgrade;
        proxy_set_header Connection "upgrade";
    }
}

Процес роботи

  1. Аналітика — збираємо архітектуру, метрики поточного навантаження, визначаємо алгоритм і кількість upstream-серверів.
  2. Проектування — проектуємо конфігурацію, узгоджуємо health checks, timeout-и, політики retry.
  3. Реалізація — налаштовуємо Nginx, розгортаємо через GitOps (Ansible/Terraform), перевіряємо на staging.
  4. Тестування — навантажувальне тестування, перевірка failover, моніторинг.
  5. Деплой — blue-green або canary rollout з нульовим downtime.

Строки та вартість

Стандартний проект (до 5 upstream-серверів) займає від 1 до 3 днів. Вартість розраховується індивідуально — залежить від складності конфігурації, необхідності sticky sessions та інтеграції з моніторингом. Замовте налаштування балансування у професіоналів — залиште заявку на сайті.

Що входить у роботу

  • Налаштування Nginx L4/L7 балансування з обраним алгоритмом.
  • Health checks і failover.
  • Cookie-based sticky sessions (при необхідності).
  • Моніторинг (stub_status + Prometheus, або налаштування Datadog).
  • Документація конфігурації та процедури експлуатації.
  • Навчання вашої команди основам підтримки.
  • 2 тижні післяпускової підтримки.

Гарантія та досвід

Наші інженери мають сертифікати NGINX і Kubernetes, а за плечима — понад 50 реалізованих проектів з балансування. Налаштування закріплюється SLO з гарантією відмовостійкості.

Отримайте консультацію експерта — зв'яжіться з нами, щоб обговорити вашу архітектуру. Ми допоможемо вибрати правильний алгоритм і налаштувати моніторинг.

Джерело: Балансування навантаження

Наші компетенції:

Останні роботи

  • Розробка сайту компанії B2B ADVANCE
    Розробка сайту компанії B2B ADVANCE
    1542
  • Розробка веб-додатків для компанії FEEDME
    Розробка веб-додатків для компанії FEEDME
    1394
  • Розробка веб-сайту для компанії БЕЛФІНГРУП
    Розробка веб-сайту для компанії БЕЛФІНГРУП
    1081
  • Розробка інтернет магазину для компанії FURNORO
    Розробка інтернет магазину для компанії FURNORO
    1369
  • Розробка логотипу компанії B2B Advance
    Розробка логотипу компанії B2B Advance
    816
  • Розробка веб-додатків для компанії Enviok
    Розробка веб-додатків для компанії Enviok
    1142