Настраиваем Internal Load Balancer через Deployment Manager

Прикольно, как некоторые относительно продвинутые инструменты и фрейморки стараются выглядеть проще и понятнее, и в результате превращаются во что-то ещё более зубодробительно невнятное. Давным-давно так было с git, когда мне пришлось перейти на командную строку и прочитать ‘Pro GIT’ целиком, чтобы гитовские GUI клиенты обрели хоть какую-то логику. Та же ерунда позже получилась с kubernetes, когда с более «простыми» kubectl run и kubectl expose было совсем непонятно, что же происходит на самом деле, в то время как перейдя на уровень ниже, к kubectl apply и YAML конфигурациям, всё стало на удивление простым логичным.

И вот теперь пришла очередь гугловых балансировщиков нагрузки — GCP load balancers. Глядя на все эти чекбоксы и кнопочки в гугловых визардах, я иногда чувствую себя младшим бухгалтером советского колхоза. С одной стороны, непонятно, что же именно я делаю. С другой стороны, непонятно — зачем. А вот как только создашь всё руками через файлы конфигурации, так всё снова кажется логичным.

Визард создания балансировщика нагрузки

Для примера возьмём, например, Internal Load Balancer, и посмотрим, как его можно сконфигурировать через Deployment Manager. Если всё пройдёт как я думаю, то оно действительно будет выглядеть логичным.

Что такое Internal Load Balancer (ILB)

Идея ILB вполне себе простая: мы будем распределять входящие запросы между несколькими виртуальными машинами — инстансами, и при этом и инстансы, и запросы будут находиться в одной и той же сети. Зачем такое может быть? Ну, например, один приватный микросервис захочет общаться с другим, который, к головной боли окружающих, масштабируется горизонтально.

Вот так выглядела бы очень упрощённая диаграмма такого общения.

internal load balancer с чёрной магией

Сверху на общую айпишку приходят запросы, и при помощи чёрной магии распределяются по конкретным хостам. И вот именно чёрная магия нас сейчас больше всего и интересует.

Разбираем магию.

Вообще говоря, в ILB не так уж и много составных частей. Секретные ингредиенты там вот какие:

  1. forwarding rule,
  2. backend service и health check,
  3. managed instance group и шаблон instance для неё.

На всё это можно ещё повесить статическую внутреннюю айпишку, но можно обойтись и эфемерной.

Посмотрим теперь на эти компоненты в обратном порядке.

Managed instance group и instance template.

Managed instance group (MIG) — это гугловый ресурс, который будет поддерживать заданное число виртуальных машин, которые он сам же создаст из шаблона. То есть, если я захочу создать десять идентичных виртуальных машин, то мне не нужно десять раз повторять одну и ту же команду или прокликивать одни и те же формы. Создал шаблон, сконфигурировал группу, задал ей  targetSize в 10, и поехали. Именно MIG будет разговаривать с остальными кусками load balancer’а.

Вообще говоря, балансировку нагрузки можно было бы сделать и среди неуправляемой группы инстансов (unmanaged), но в таком случае все десять виртуальных машин действительно пришлось бы создавать руками. Да и автоматически масштабировать такие группы не получится. autoscaler — ещё один облачный ресурс — работает только с управляемыми группами).

Вот как создание управляемой группы и шаблона инстанса для неё выглядит в deployment manager:

Да, ещё один момент: internal load balancer — штука региональная, поэтому и MIG ей нужен соответствующий — regionalInstanceGroupManager.

backend service и health check для него

Бэкэнд сервис — это уже группа из одного или нескольких MIG, которые предоставляют один и тот же сервис. Например, API, контент, или что-нибудь ещё. На уровне сервиса мы и будем указывать, как именно распределять запросы между этими группами. Будет ли это INTERNAL или EXTERNAL балансировка, какой там будет протокол, по какому правилу распределять запросы, и прочее.

Бэкенду также полагается health check, чтобы он мог хоть как-то различать, кто ещё в состоянии принимать траффик, а кто уже не жилец. Неочевидная особенность таких проверок — им нужны отдельные правила файрвола, которые автоматически не проставляются, и поэтому их нужно задавать вручную (ну или через deployment manager).

Наш балансировщик — INTERNAL, протокол — TCP (ILB всего-то два протокола поддерживает: TCP и UDP), так что забросим-ка ещё немного YAML в конфигурацию и посмотрим, на что это теперь похоже:

Как в случае с regionInstanceGroupManager, сервис тоже региональный — regionBackendService, и он находится в том же регионе, что и MIG. Ну а начинается YAML с задания правил файрвола, чтобы health checks таки смогли пробиться к инстансам.

forwarding rule и статическая айпишка

Последний ресурс — forwarding rule — соединяет вместе айпишку с одной стороны и получателя траффика с неё с другой. Настраивать его проще простого, поэтому для разнообразия пусть он хотя бы пользуется статический региональной айпишкой:

Результат

Вот на что в результате стал похож наш internal load balancer:

internal load balancer без чёрной магии

Разноцветных прямоугольников там больше, чем хотелось бы, но при некотором ментальном усилии во всём этом теперь можно разглядеть смысл. Теперь мы можем отправить YAML в Deployment Manager, создать какую-нибудь тестовую виртуальную машину в той же сети, что и ILB (в нашем случае это — default), найти адрес нашей статический айпишки (gcloud compute addresses list) и начать развлекаться:

Развёртываем:

Находим айпишку:

Отправляем пару тестовых запросов на неё:

Вуаля! Штука работает. И даже в гугловой консоли оно всё похоже на настоящий GCP балансировщик нагрузки:

Google Cloud Console

Хотите верьте, хотите нет, но на самом деле это один из самых простых лоад балансеров в GCP. Чтобы доказать это, в следующий раз я таким же образом препарирую какой-нибудь внешний глобальный HTTP(s) балансировщик, и тогда посмотрим, на что это будет похоже.

2 комментария для “Настраиваем Internal Load Balancer через Deployment Manager

  1. Хороший блог. Спасибо. Про облака и инстансы с LB вообще песня. Правда я юзаю AWS, но разница не шибко большая. Пиши побольше об этом. Ну и ELS тоже полезно)).

Добавить комментарий

Ваш адрес email не будет опубликован. Обязательные поля помечены *