Назад | Перейти на главную страницу

Как создать внутренний / частный балансировщик нагрузки в вычислительном движке Google

У меня два кластера. Кластер A (на движке контейнеров Google) - это общедоступный кластер, и ему необходимо подключиться к частному кластеру B (кластер для развертывания по щелчку на GCE), чтобы получить доступ к службе. Я хотел бы, чтобы кластер A подключался к кластеру B через балансировщик нагрузки, и это может работать, даже если кажется, что всем балансировщикам нагрузки GCE требуется общедоступный IP-адрес. https://groups.google.com/d/topic/gce-discussion/Dv6289i4_rg/discussion (Я бы предпочел, чтобы все это было приватным).

Общедоступный IP-адрес сам по себе не так уж и плох, если бы вы могли просто установить простое правило брандмауэра и использовать стандартный Google Load Balancer. К сожалению, исходные теги, похоже, не пересекают порог WAN (или просто не проходят балансировщик нагрузки). Это правило, которое я бы хотел использовать:

gcloud compute firewall-rules create servicename-lb-from-gke-cluster --allow tcp:1234 --source-tags k8s-gke-cluster-node --target-tags servicename #DOES NOT WORK

После ввода указанной выше команды кластер A не может взаимодействовать с кластером B (через балансировщик нагрузки) через TCP-порт 1234.

Это действительно работает, но это болезненно, потому что требует надзора для автоматизации настройки общедоступных IP-адресов исходного кластера:

gcloud compute firewall-rules create servicename-lb-from-gke-cluster --allow tcp:1234 --source-ranges 100.2.3.4/32 100.3.5.9/32 100.9.1.2/32 --target-tags servicename #Does work, but is painful

Как было предложено в ветке групп Google, еще одно предложение - прокси-сервер HA.

Другая идея - открыть брандмауэр для всей WAN и добавить безопасную аутентификацию между кластерами A и B. Может быть, это в любом случае хорошая идея из соображений безопасности? Сложность может варьироваться от легкой до сложной, в зависимости от того, какие кластеры A и B запущены - было бы неплохо иметь более общее решение.

Есть ли у кого-нибудь идеи получше? У кого-нибудь еще есть такая же проблема?

Прошу прощения за сложность! Я не эксперт по брандмауэрам Compute Engine, но полагаю, что вы правы насчет ограничений исходных тегов, которые работают только для внутреннего трафика.

Команда Kubernetes осознает, что координировать несколько кластеров сложно, и мы начинаем работать над решениями, но, к сожалению, у нас пока нет ничего особенно надежного и полезного для вас.

А пока есть хитрый способ балансировки нагрузки трафика от одного кластера к другому, не требуя Google Cloud Load Balancer или чего-то вроде haproxy. Вы можете указать внутренний IP-адрес одного из узлов в кластере B (или IP-адрес маршрута GCE, который направляет трафик на один из узлов в кластере B) в Поле PublicIPs службы, с которой вы хотите поговорить. Затем попросите кластер A отправлять свои запросы на этот IP-адрес через порт службы, и они будут сбалансированы по всем модулям, поддерживающим службу.

Это должно работать, потому что на каждом узле кластера kubernetes работает так называемый kube-proxy, который автоматически проксирует трафик, предназначенный для IP-адреса службы, и переносит на поды, поддерживающие службу. Пока PublicIP находится в определении сервиса, kube-proxy будет балансировать трафик за вас.

Если вы остановитесь на этом, он будет настолько надежным, насколько надежен узел, IP-адрес которого вы отправляете трафик (но надежность одного узла на самом деле довольно высока). Однако, если вы хотите по-настоящему фантазировать, мы можем сделать вещи немного более надежными, балансируя нагрузку с кластера A на все узлы в кластере B.

Чтобы это работало, вы должны поместить все внутренние IP-адреса всех узлов кластера B (или маршруты ко всем внутренним IP-адресам узлов) в поле PublicIPs вашей службы. Затем в кластере A вы можете создать отдельную службу с пустым селектором меток и заполнить в нем поле конечных точек вручную, когда вы создаете его с парой (IP, порт) для каждого IP в кластере B. Селектор пустой метки предотвращает инфраструктура kubernetes от перезаписи введенных вручную конечных точек, а также kube-proxy в кластере A будут балансировать нагрузку трафика для службы по IP-адресам кластера B. Это стало возможным благодаря PR № 2450, если вам нужен более подробный контекст.

Дайте мне знать, если вам понадобится дополнительная помощь в этом вопросе!

Теперь это возможно с официальным GCP Internal LB: https://cloud.google.com/compute/docs/load-balancing/internal/

В частности, вот документация kubernetes (GKE): https://cloud.google.com/kubernetes-engine/docs/how-to/internal-load-balancing

Обратите внимание на служебную аннотацию:

  annotations:
    cloud.google.com/load-balancer-type: "Internal"

Обратите внимание, что, хотя этот LB уже доступен только для внутреннего использования, если вы хотите дополнительно ограничить, например, свои кластерные модули вы можете сделать примерно так:

loadBalancerSourceRanges: 10.4.0.0/14

Чтобы получить диапазон IP-адресов вашего модуля, вы можете запустить: gcloud container clusters describe $CLUSTER_NAME |grep clusterIpv4Cidr