API Load Balancer as a Service#
graph TD
%% Основная сущность Load Balancer
LB[Load Balancer]
%% Компоненты Vhost
V1[Vhost]
V2[Vhost]
%% Компоненты Route
R1[Route]
R2[Route]
R3[Route]
%% Компоненты Backend Pool
BP1[Backend Pool]
BP2[Backend Pool]
%% Отношения, показывающие полную структуру
LB -->|содержит| V1
LB -->|содержит| V2
V1 -->|определяет| R1
V1 -->|определяет| R2
V2 -->|определяет| R3
R1 -->|использует| BP1
R2 -->|использует| BP2
R3 -->|использует| BP1
%% Легенда
class LB main
class V1,V2 component
class R1,R2,R3 route
class BP1,BP2 backend
Обзор#
Сервис Load Balancer предоставляет REST API для создания и управления конфигурациями балансировщиков нагрузки. Он поддерживает протоколы Layer 4 (L4) и Layer 7 (L7) с различными возможностями маршрутизации.
Основные компоненты#
Load balancer: логический экземпляр LBVhost: как принимать входящий трафикRoute: как обогащать запросы и куда их направлять (например, на какой backend)Backend pools: адреса, куда мы можем отправлять запросы
Load Balancer (LB)#
Основная сущность балансировщика нагрузки, управляющая:
- Статусом (NEW, IN_PROGRESS, ACTIVE, ERROR)
- IP-адресами
- Конфигурацией типа:
core— VM-based LBcore_agent— LB будет запущен на самом экземпляре exordos_core
Vhost#
Конфигурация виртуального хоста, определяющая:
- Протокол (http, https, tcp, udp)
- Порт
- Домены (для L7 протоколов)
- Сертификат (для HTTPS)
- Внешние источники (SSH forwarding)
Backend Pool#
Пул бэкендов, управляющий:
- Список конечных точек бэкендов
- Алгоритм балансировки нагрузки (roundrobin)
Route#
Правила маршрутизации, определяющие, как обрабатывается трафик:
- Типы условий
prefix— nginx-подобные regex префиксыexact— простое точное совпадениеregex— nginx-подобный regexraw— используется для установки пулов бэкендов для L4
- Действия
backend— отправить на бэкендredirect— вернуть http-редиректlocal_dir— отдавать статические файлы из локальной директории на LBlocal_dir_download— скачать tar.gz/zstd на сам LB, распаковать и отдавать данные из локальной директории
- Модификаторы (заголовки, правила rewrite)
headers— модифицировать заголовкиauto_header:- X-Forwarded-For
- X-Forwarded-Port
- X-Forwarded-Proto
- X-Forwarded-Prefix
set_header: установить статический заголовок
Структура API#
Создание балансировщика нагрузки#
{
"name": "my-load-balancer",
"description": "Production load balancer",
"type": {
"kind": "core",
"cpu": 2,
"ram": 1024,
"disk_size": 20,
"nodes_number": 2
}
}
Создание виртуального хоста#
{
"name": "web-vhost",
"description": "Web server vhost",
"protocol": "http",
"port": 80,
"domains": ["example.com", "www.example.com"],
"external_sources": [
{
"kind": "ssh_forward",
"host": "10.0.0.10",
"port": 22,
"user": "admin",
"private_key": "-----BEGIN RSA PRIVATE KEY-----\\n..."
}
]
}
Требования к внешним источникам#
SSH#
Проверено на Ubuntu 24, подготовьте удалённую систему:
# Можем использовать nginx с proxy_protocol и socat для udp
apt install nginx-full socat
# Применить привязку к привилегированным портам
echo 'net.ipv4.ip_unprivileged_port_start=0' > /etc/sysctl.d/50-unprivileged-ports.conf
sysctl --system
Создание пула бэкендов#
{
"name": "web-backend-pool",
"endpoints": [
{
"kind": "host",
"host": "10.0.1.10",
"port": 80,
"weight": 1
},
{
"kind": "host",
"host": "10.0.1.11",
"port": 80,
"weight": 1
}
],
"balance": "roundrobin"
}
Создание маршрутов#
Маршрут на основе префикса#
{
"name": "api-prefix-route",
"condition": {
"kind": "prefix",
"value": "/api",
"actions": [
{
"kind": "backend",
"pool": "backend-pool-uuid"
}
]
}
}
Маршрут с точным совпадением#
{
"name": "exact-route",
"condition": {
"kind": "exact",
"value": "/login",
"actions": [
{
"kind": "redirect",
"url": "https://example.com/login",
"code": 301
}
]
}
}
Правила валидации#
Валидация Vhost#
- L7 протоколы (http, https) должны иметь хотя бы один домен
- HTTPS протокол требует сертификат
- L4 протоколы не поддерживают домены или сертификаты
- Комбинации protocol+port должны быть уникальными
Валидация маршрутов#
- L7 протоколы не могут иметь raw маршруты
- L4 протоколы могут иметь только raw маршруты
- Маршруты должны проходить валидацию относительно ограничений родительского vhost
Пример манифеста элемента#
Примеры:
Базовый манифест для https-сайта (предположим, что некоторые узлы уже существуют):
...
requirements:
core:
from_version: "0.0.0"
imports:
core_public_domain:
element: "$core"
kind: "resource"
link: "$core.dns.domains.$public_domain"
$core.network.lb:
basic_lb:
project_id: "12345678-c625-4fee-81d5-f691897b8142"
type:
kind: core
ram: 1024
cpu: 2
$core.network.lb.$basic_lb.backend_pools:
basic_backend_http:
project_id: "12345678-c625-4fee-81d5-f691897b8142"
parent: $core.network.lb.$basic_lb:uuid
endpoints:
- kind: host
host: $core.compute.nodes.$exordos_basic:default_network:ipv4
port: 80
$core.network.lb.$basic_lb.vhosts:
basic_http:
project_id: "12345678-c625-4fee-81d5-f691897b8142"
parent: $core.network.lb.$basic_lb:uuid
domains:
- f"example.{$basic.imports.$core_public_domain:name}"
- f"www.example.{$basic.imports.$core_public_domain:name}"
protocol: http
port: 80
basic_https:
project_id: "12345678-c625-4fee-81d5-f691897b8142"
parent: $core.network.lb.$basic_lb:uuid
domains:
- f"example.{$basic.imports.$core_public_domain:name}"
- f"www.example.{$basic.imports.$core_public_domain:name}"
protocol: https
port: 443
cert:
kind: raw
crt: $core.secret.certificates.basic_cert:cert
key: $core.secret.certificates.basic_cert:key
$core.network.lb.$basic_lb.vhosts.$basic_http.routes:
basic_http_route:
project_id: "12345678-c625-4fee-81d5-f691897b8142"
parent: $core.network.lb.$basic_lb.vhosts.$basic_http:uuid
condition:
kind: prefix
value: /
actions:
- kind: redirect
url: f"https://example.{$basic.imports.$core_public_domain:name}"
$core.network.lb.$basic_lb.vhosts.$basic_https.routes:
basic_https_route:
project_id: "12345678-c625-4fee-81d5-f691897b8142"
parent: $core.network.lb.$basic_lb.vhosts.$basic_https:uuid
condition:
kind: prefix
value: /
actions:
- kind: backend
pool: $core.network.lb.$basic_lb.backend_pools.$basic_backend_https:uuid
$basic.imports.$core_public_domain.records:
basic_a_record:
domain: "$basic.imports.$core_public_domain:uuid"
project_id: "12345678-c625-4fee-81d5-f691897b8142"
type: "A"
record:
kind: "A"
name: "example"
address: "$core.network.lb.$basic_lb:index(ipsv4, 0)"
$core.secret.certificates:
basic_cert:
name: basic_cert
project_id: "12345678-c625-4fee-81d5-f691897b8142"
email: user@exordos.com
domains:
f"example.{$basic.imports.$core_public_domain:name}"
f"*.example.{$basic.imports.$core_public_domain:name}"