Перейти к содержанию

Стандартные возможности

Извлечение образцов, карты отображения, ACL, переключение содержимого, таблицы привязок, переписывание и защита серверов

В этом разделе перечислены возможности, широко используемые в HAProxy, но не обязательно присутствующие в других балансировщиках нагрузки.

3.4.1. Стандартные возможности: извлечение и преобразование сведений

HAProxy поддерживает получение сведений с помощью широкого набора функций извлечения образцов. Они извлекают отдельные сведения, называемые образцами, для немедленного использования. Это применяется для привязки сеансов, построения условий, вывода сведений в журналы или дополнения заголовков HTTP.

Образцы можно извлекать из разных источников:

  • Константы: целые числа, строки, IP-адреса, двоичные блоки.

  • Процесс: дата, переменные окружения, состояние сервера/фронтенда/бэкенда/процесса, число и интенсивность передачи байтов/соединений, длина очереди, генератор случайных чисел и т. п.

  • Переменные: на уровне сеанса, запроса или ответа.

  • Клиентское соединение: исходные и целевые адреса и порты и все связанные статистические счётчики.

  • Клиентский сеанс SSL: протокол, версия, алгоритм, шифр, размер ключа, идентификатор сеанса, все поля сертификатов клиента и сервера, серийный номер сертификата, SNI, ALPN, NPN, поддержка клиентом определённых расширений.

  • Содержимое буферов запроса и ответа: произвольная полезная нагрузка по смещению и длине, длина данных, cookie RDP, декодирование типа приветствия SSL, декодирование TLS SNI.

  • HTTP, запрос и ответ: метод, URI, путь, аргументы строки запроса, код состояния, значения заголовков, значение заголовка по позиции, cookie, захваченные значения, аутентификация, элементы тела.

Затем образец может пройти через операторы, называемые преобразователями. Преобразователь принимает образец и создаёт новый, возможно совершенно другого типа. Например, он может вернуть целочисленную длину входной строки или перевести строку в верхний регистр. До окончательного использования к образцу можно последовательно применить любое число преобразователей. Среди доступных чаще всего используются:

  • Арифметические и логические операторы для сложных вычислений над входными данными: отношений, процентов или просто перевода между единицами измерения.

  • Маски IP-адресов, полезные для объединения адресов в более крупные сети.

  • Представление данных: декодирование URL, base64, шестнадцатеричный формат, строки JSON, хеширование.

  • Преобразование строк: извлечение подстрок по фиксированным позиции и длине, отдельных полей по разделителям и определённых слов, смена регистра, замена по регулярным выражениям.

  • Преобразование дат: в формат даты HTTP, из местного времени в UTC и обратно, добавление и вычитание смещения.

  • Поиск записи в таблице привязок для получения статистики или назначенного сервера.

  • Преобразование ключа в значение по карте отображения из файла, преимущественно для геолокации.

3.4.2. Стандартные возможности: карты отображения

Карты отображения — мощный тип преобразователя. При запуске в память загружается файл с двумя столбцами, затем каждый входной образец ищется в первом столбце. Если запись найдена, возвращается соответствующее значение из второго столбца, иначе — значение по умолчанию. Результат тоже является образцом, поэтому к нему можно применять последующие преобразования, включая поиск в других картах. Чаще всего карты используют для преобразования IP-адреса клиента в номер AS или код страны, поскольку они поддерживают наиболее длинное совпадение сетевых адресов, но возможны и многие другие применения.

Одно из их преимуществ — обновление на лету через CLI или определённые действия с использованием других образцов. Это позволяет хранить и извлекать сведения между последовательными обращениями. Другое преимущество — индексирование на основе двоичных деревьев: даже при сотнях тысяч записей поиск чрезвычайно быстр, поэтому геолокация требует мало ресурсов и легко настраивается.

3.4.3. Стандартные возможности: ACL и условия

Большинство операций HAProxy может выполняться условно. Условия строятся объединением нескольких ACL логическими операторами AND, OR и NOT. Каждая ACL представляет собой последовательность проверок на основе следующих элементов:

  • Метод извлечения образца для получения проверяемого элемента.

  • Необязательная последовательность преобразователей элемента.

  • Список шаблонов для сопоставления.

  • Метод сопоставления, определяющий способ сравнения шаблонов с образцом.

Например, образец можно получить из заголовка HTTP «Host», перевести в нижний регистр, а затем сопоставить с несколькими регулярными выражениями соответствующим методом.

Технически ACL построены на той же основе, что карты отображения: у них одинаковые внутренние структуры, методы сопоставления шаблонов и производительность. Единственное существенное отличие: вместо образца они возвращают только «found» или «not found». Шаблоны ACL можно объявлять прямо в конфигурации, отдельный файл не требуется. Для удобства и понятности конфигурации ACL можно именовать. Именованную ACL можно объявить несколько раз: все определения будут проверяться по очереди до первого совпадения.

Предоставляется около 13 методов сопоставления шаблонов, включая маску IP-адреса, диапазоны целых чисел, подстроки и регулярные выражения. Они работают как функции, и, как в любом языке программирования, вычисляется только необходимое. Если условие с OR уже истинно, следующие части не вычисляются; если условие с AND уже ложно, оставшаяся часть также не вычисляется.

Практического ограничения на число объявленных ACL нет, и несколько часто используемых ACL предоставляются готовыми. Однако опыт показывает, что конфигурации с множеством именованных ACL трудно отлаживать. Иногда проще использовать анонимные ACL прямо в правилах, поскольку приходится реже обращаться к определениям вне анализируемой области.

3.4.4. Стандартные возможности: переключение содержимого

HAProxy реализует механизм переключения на основе содержимого. Соединение или запрос поступает во фронтенд, затем обрабатываются переданные с ним сведения. На их основе можно задать условия ACL для выбора бэкенда, который обработает запрос. Так трафик направляется в разные бэкенды в зависимости от содержимого запроса. Типичный пример — использование заголовка Host и/или частей пути (подкаталогов либо расширений файлов), чтобы определить, относится ли запрос HTTP к статическому объекту или приложению. Статические объекты направляются в бэкенд из быстрых лёгких серверов, а остальной трафик — на более сложный сервер приложений. Получается гибкая схема виртуального хостинга, удобная для объединения нескольких технологий в общее решение.

Другой вариант применения — выбор алгоритма балансировки по разным критериям. Например, кеш может использовать хеш URI, а приложение — round-robin.

Наконец, механизм позволяет нескольким заказчикам использовать небольшие доли общего ресурса, ограничивая число соединений для каждого бэкенда, а значит, и заказчика.

Правила переключения содержимого хорошо масштабируются, хотя производительность зависит от числа и сложности ACL. Можно также использовать динамические правила, в которых значение образца напрямую преобразуется в имя бэкенда, вообще без ACL. Сообщалось об успешной работе таких конфигураций в рабочей среде как минимум с 300000 бэкендов.

3.4.5. Стандартные возможности: таблицы привязок

Таблицы привязок обычно хранят сведения о привязке сеансов — ссылку на сервер, куда был направлен посетитель. Ключом служит связанный с посетителем идентификатор: исходный адрес, идентификатор SSL соединения, cookie HTTP или RDP, номер заказчика из URL или полезной нагрузки и т. п. Сохраняемое значение — идентификатор сервера.

Таблицы привязок поддерживают 3 типа образцов в ключах: целые числа, строки и адреса. В прокси можно ссылаться только на одну таблицу привязок, везде обозначаемую именем прокси. Параллельно можно отслеживать до 8 ключей. Идентификатор сервера фиксируется при обработке запроса или ответа, когда известны и ключ, и сервер.

Содержимое таблиц может реплицироваться в режиме active-active с другими узлами HAProxy, называемыми «peers», а при перезагрузке конфигурации — также с новым процессом. Тогда все узлы балансировки имеют одинаковые сведения и принимают одинаковые решения о маршрутизации, даже если запросы клиента распределяются между несколькими узлами.

Поскольку таблицы индексируются по признаку, позволяющему распознать клиента, в них часто хранят и дополнительные сведения, например статистику по клиентам. Дополнительная статистика занимает место и должна объявляться явно. Можно хранить входящую и исходящую пропускную способность, число одновременных соединений, интенсивность и число соединений за период, количество и частоту ошибок, специальные метки и счётчики и т. п. Чтобы сохранять такие сведения без обязательной привязки к серверу, реализована специальная функция отслеживания. Она позволяет одновременно отслеживать до 3 ключей из разных таблиц независимо от правил привязки. Любую сохраняемую статистику можно искать, выгружать и очищать через CLI, расширяя возможности устранения неполадок в реальном времени.

Хотя этот механизм позволяет повышать приоритет возвращающегося посетителя или менять качество обслуживания в зависимости от хорошего или плохого поведения, чаще всего его используют для борьбы со злоупотреблениями и DDoS. Он позволяет строить сложные модели выявления нежелательного поведения при высокой скорости обработки.

3.4.6. Стандартные возможности: форматированные строки

HAProxy работает со строками во многих местах: в журналах, перенаправлениях, добавляемых заголовках и т. п. Для максимальной гибкости введены форматированные строки, первоначально для журналирования, поэтому механизм до сих пор называется «log-format». Такие строки содержат управляющие последовательности для вставки динамических данных, включая переменные и выражения извлечения образцов, и даже изменения кодирования при преобразовании результата в строку, например добавления кавычек. Это мощное средство формирования заголовков, данных ответа и даже шаблонов ответов, а также настройки строк журнала. Чтобы обычные строки оставались простыми в составлении, предусмотрено около 50 специальных меток — сокращений для часто используемых в журналах сведений.

3.4.7. Стандартные возможности: переписывание HTTP и перенаправления

Установка балансировщика перед приложением, которое на это не рассчитано, без подходящих инструментов может оказаться сложной. Одна из самых частых задач — изменить заголовки запросов и ответов, чтобы балансировщик выглядел исходным сервером, и исправить жёстко заданные сведения. Сюда относятся изменение пути запроса (что настоятельно не рекомендуется), поля Host, поля Location в ответах перенаправления, атрибутов пути и домена cookie и т. п. Также многие серверы слишком многословны и раскрывают в ответах лишние сведения, повышая уязвимость к целевым атакам. Хотя теоретически очищать ответы не задача балансировщика, на практике он расположен в наиболее удобной точке инфраструктуры для гарантированной очистки.

Иногда балансировщику также нужно перехватить запрос и ответить перенаправлением на новый URL. Перенаправление и переписывание иногда путают, но это совершенно разные понятия: при переписывании клиент и сервер видят разные данные и по-разному представляют расположение страницы, а перенаправление просит клиента обратиться к новому URL, чтобы он видел то же расположение, что и сервер.

Для этого HAProxy поддерживает разные возможности переписывания и перенаправления, в том числе:

  • Переписывание URL и заголовков запросов и ответов по регулярным выражениям. Это самый распространённый способ изменения значений заголовков благодаря понятности и удобству регулярных выражений.

  • Добавление, удаление или замена заголовков на основе форматированных строк для передачи сведений, например алгоритма и шифра TLS на стороне клиента.

  • Перенаправления HTTP с любым кодом 3xx на относительный, абсолютный или полностью динамический URI из форматированной строки.

  • Дополнительные параметры перенаправлений: установка или удаление cookie, отбрасывание строки запроса, добавление отсутствующей завершающей косой черты и т. п.

  • Мощная директива «return», позволяющая настроить любую часть ответа — состояние, заголовки, тело — с динамическим содержимым или даже файлами шаблонов.

  • Условия на основе ACL для всех операций.

3.4.8. Стандартные возможности: защита серверов

HAProxy стремится максимально повысить доступность службы и для этого защищает серверы от перегрузки и атак. Первый и самый важный принцип: серверам пересылаются только полные корректные запросы. Прежде всего HAProxy должен найти элементы протокола, необходимые для синхронизации с потоком байтов. Кроме того, пока запрос не получен полностью, нельзя знать, не изменят ли некоторые элементы его смысл. Прямое преимущество — серверы не получают некорректные или неполные запросы. Это очень эффективная защита от атак slowloris, практически не влияющих на HAProxy.

Другой важный момент — буферы HAProxy для запросов и ответов. Отправляя запрос серверу только после полного получения и быстро считывая весь ответ из локальной сети, HAProxy занимает соединение с сервером на очень короткое время, максимально сохраняя его ресурсы.

Из этого непосредственно следует возможность искусственно ограничивать число одновременных соединений или незавершённых запросов к серверу. Это гарантирует отсутствие перегрузки, даже если во время всплесков трафика сервер непрерывно работает на 100% мощности. Все лишние запросы просто ждут в очереди освобождения места. Такая огромная экономия ресурсов обычно настолько улучшает время ответа, что работа оказывается быстрее, чем при перегрузке сервера. Запросы из очереди можно перераспределять на другие серверы или даже отменять в очереди при отказе клиента от запроса. Это защищает и от «эффекта обновления страницы»: каждый щелчок «обновить» на медленно загружаемой странице обычно создаёт новый запрос и поддерживает перегрузку.

Механизм slow-start также защищает перезапускаемые серверы от интенсивного трафика, пока они ещё завершают запуск или компилируют классы.

На уровне протокола парсер HTTP можно ослабить, чтобы принимать не соответствующие стандарту, но безвредные запросы и ответы и даже исправлять их. Это сохраняет доступность ошибочных приложений на время разработки исправления. Одновременно проблемные сообщения полностью захватываются с подробным отчётом, помогающим разработчикам найти ошибку. Наиболее опасные нарушения протокола корректно выявляются, обрабатываются и исправляются. Например, некорректный запрос или ответ с двумя заголовками Content-length исправляется, если их значения в точности совпадают, и отклоняется при различии, поскольку это уже угроза безопасности. Анализ протокола не ограничен HTTP: он доступен и для других протоколов, например TLS или RDP.

При обнаружении нарушения протокола или атаки возможны разные реакции: обычный ответ «HTTP 400 bad request», закрытие соединения сбросом TCP или имитация ошибки после длительной задержки — ловушка соединений («tarpit»), сбивающая атакующего с толку. Всё это защищает серверы, делая продолжение атаки слишком затратным для нарушителя.

HAProxy также предлагает более сложные средства защиты от случайных утечек данных и смешения сеансов. Он может не только записывать подозрительные ответы сервера, но и журналировать и при необходимости блокировать ответ, угрожающий конфиденциальности посетителя. Например, кешируемый cookie в кешируемом ответе может быть выдан промежуточным кешем другому посетителю, случайно предоставив общий доступ к сеансу.