Go: Балансировка нагрузки

5 вопросов

1 Алгоритмы балансировки нагрузки. Round-robin, least connections.

Round-robin - поочередная выдача запросов по списку бэкендов. Least connections - выбор бэкенда с наименьшим числом активных соединений. Weighted round-robin - с весами. IP hash - один клиент всегда на один бэкенд (sticky). В Go при реализации клиентского балансера хранят список адресов и индекс (atomic для round-robin) или счетчики соединений.

var idx uint32
next := atomic.AddUint32(&idx, 1)
backend := backends[next%uint32(len(backends))]
Открыть отдельно →
2 Балансировка L4 и L7. Разница.

L4 (транспортный уровень) - по IP и порту, без разбора содержимого. Быстро, подходит для TCP/любого протокола. L7 (прикладной) - по HTTP (host, path, заголовки); можно маршрутизировать по URL и делать health check по HTTP. В Go обращение к бэкендам обычно через L7 (HTTP-клиент к балансировщику или свой роутер по path).

Открыть отдельно →
3 Nginx как балансировщик перед Go-сервисами.

Nginx в роли reverse proxy: upstream с несколькими server (Go-инстансы), балансировка по умолчанию round-robin. Health check: max_fails и fail_timeout. Для WebSocket и long polling - proxy_read_timeout, proxy_http_version 1.1, Upgrade. В Go приложение должно корректно закрывать соединения и отдавать health endpoint для Nginx.

upstream go_backend {
    server 127.0.0.1:8081;
    server 127.0.0.1:8082;
    server 127.0.0.1:8083 backup;
}
Открыть отдельно →
4 HAProxy перед Go. Основные настройки.

HAProxy - балансировщик и reverse proxy. Backend - группа серверов, frontend - привязка к порту и правилам. Режимы: round-robin, leastconn. Health check через option httpchk и uri. Для Go важен timeout (client, server), и правильный health endpoint. Статистика через stats uri. Подходит для TCP и HTTP.

backend go_servers
    balance roundrobin
    option httpchk GET /health
    server s1 10.0.0.1:8080 check
    server s2 10.0.0.2:8080 check
Открыть отдельно →
5 Connection pooling в Go при обращении к бэкендам.

HTTP-клиент в Go переиспользует соединения (Transport с пулом). Один клиент на приложение или на пул воркеров; не создавать клиент на каждый запрос. Настройки: MaxIdleConnsPerHost, IdleConnTimeout. При обращении к одному бэкенду через балансировщик пул на стороне Go ограничивает число соединений и снижает накладные расходы на TCP/TLS handshake.

client := &http.Client{
    Transport: &http.Transport{
        MaxIdleConnsPerHost: 100,
        MaxConnsPerHost:     100,
    },
}
Открыть отдельно →
🧠Квиз 🏆Лидеры 🎯Собесед. 📖Вопросы 📚База зн.