- PVSM.RU - https://www.pvsm.ru -

Представляем Kubernetes CCM (Cloud Controller Manager) для Яндекс.Облака

Представляем Kubernetes CCM (Cloud Controller Manager) для Яндекс.Облака - 1

В продолжение к недавнему релизу CSI-драйвера [1] для Яндекс.Облака мы публикуем ещё один Open Source-проект для этого облака — Cloud Controller Manager [2]. CCM необходим не только для кластера в целом, но и собственно CSI-драйвера. Подробности о его предназначении и некоторые особенности реализации — под катом.

Введение

Зачем это?

Мотивы, побудившие нас к разработке CCM для Яндекс.Облака, полностью совпадают с уже описанными в анонсе [1] CSI-драйвера. Мы обслуживаем множество Kubernetes-кластеров у разных облачных провайдеров, для чего используем единый инструмент. Он реализует многочисленные удобства «в обход» managed-решений этих провайдеров. Да, у нас довольно специфичный случай и потребности, однако созданные из-за них наработки могут пригодиться и другим пользователям.

Что вообще такое CCM?

Как правило, мы подготавливаем окружающую нас среду для кластера извне — например, с помощью Terraform. Но иногда есть необходимость управлять окружающей нас облачной средой из кластера. Такая возможность предусмотрена, и именно её реализует CCM [3].

В частности, Cloud Controller Manager обеспечивает пять основных типов взаимодействия:

  1. Instances – реализует связь 1:1 между объектом узла в Kubernetes (Node) и виртуальной машиной в облачном провайдере. Для этого мы:
    • заполняем поле spec.providerID в объекте Node. К примеру, для OpenStack CCM это поле имеет следующий формат: openstack:///d58a78bf-21b0-4682-9dc6-2132406d2bb0. Можно видеть имя облачного провайдера и уникальный UUID server’а (виртуальная машина в OpenStack) объекта;
    • дополняем nodeInfo в объекте Node информацией о виртуальной машине. Например, указываем instance type в AWS;
    • проверяем наличие виртуальной машины в облаке. К примеру, если объект Node перешёл в состояние NotReady, можно проверить, существует ли вообще виртуальная машина в облачном провайдере по providerID. Если её нет — удаляем объект Node, который в противном случае остался бы в кластере навечно;
  2. Zones – задаёт failure domain для объекта Node, чтобы планировщик мог выбрать узел для Pod’а согласно регионам и зонам в облачном провайдере;
  3. LoadBalancer – при создании объекта Service с типом LoadBalancer создаёт некий балансировщик, который направит трафик извне к узлам кластера. Например, в Yandex.Cloud можно использовать NetworkLoadBalancer и TargetGroup для этих целей;
  4. Route – строит сеть между узлами, т.к. по требованиям Kubernetes каждый pod должен иметь свой IP-адрес и иметь возможность достучаться до любого другого pod’а. Для этих целей можно использовать оверлейную сеть (VXLAN, GENEVE) или задать таблицу маршрутизации прямо в виртуальной сети облачного провайдера:

    Представляем Kubernetes CCM (Cloud Controller Manager) для Яндекс.Облака - 2

  5. Volume – позволяет динамически заказывать PV, используя PVC и SC. Изначально этот функционал являлся частью CCM, но ввиду большой сложности был вынесен в отдельный проект Container Storage Interface (CSI). Про CSI мы не раз писали [4] и, как уже говорилось, даже выпустили [1] CSI-драйвер.

Ранее весь код, взаимодействующий с облаком, лежал в основном Git-репозитории проекта Kubernetes по адресу k8s.io/kubernetes/pkg/cloudprovider/providers, но от этого решили отказаться из-за неудобства работы с большой кодовой базой. Все старые реализации были вынесены в отдельный репозиторий [5]. Для удобства дальнейшей поддержки и разработки все общие компоненты тоже были вынесены в отдельный репозиторий [6].

Как и в случае с CSI, многие крупные поставщики облачных услуг уже разработали свои CCM для использования облаков в Kubernetes. Если же CCM у поставщика нет, но все необходимые функции доступны через API, то можно реализовать CCM самостоятельно.

Чтобы написать свою реализацию CCM, достаточно реализовать нужные Go-интерфейсы [7].

И вот что у нас получилось [2].

Реализация

Как пришли к этому

Разработку (а точнее — даже использование) мы начали с готового(!) CCM [8] для Yandex.Cloud годовой давности.

Однако в этой реализации нам не хватало:

  • аутентификации через JWT IAM-токен;
  • поддержки Service controller’а.

По согласованию с автором (dlisin) в Telegram, мы форкнули yandex-cloud-controller-manager и дописали недостающие функции.

Основные возможности

На текущий момент CCM поддерживает следующие интерфейсы:

  • Instances;
  • Zones;
  • LoadBalancer.

В будущем, когда Yandex.Cloud начнёт работать с продвинутыми возможностями VPC, мы добавим и интерфейс Routes.

LoadBalanacer как главный вызов

Изначально мы пробовали, как у других реализаций CCM, создавать пару из LoadBalancer и TargetGroup для каждого Service с типом LoadBalancer. Однако у Yandex.Cloud обнаружилось одно интересное ограничение: нельзя использовать TargetGroups с пересекающимися Targets (пара SubnetIDIpAddress).

Представляем Kubernetes CCM (Cloud Controller Manager) для Яндекс.Облака - 3

Поэтому внутри созданного CCM запускается контроллер, который при изменении объектов Node собирает информацию обо всех интерфейсах на каждой виртуальной машине, группирует их по принадлежности к определённым NetworkID, создаёт по TargetGroup на NetworkID, а также следит за актуальностью. Впоследствии, при создании объекта Service с типом LoadBalanacer мы просто прикрепляем заранее созданную TargetGroup к новым NetworkLoadBalanacer'ам.

Как начать пользоваться?

CCM поддерживает Kubernetes версии 1.15 и выше. В кластере для его работы требуется, чтобы флаг --cloud-provider=external был установлен в значение true для kube-apiserver, kube-controller-manager, kube-scheduler и всех kubelet’ов.

Все необходимые шаги по самой установке описаны в README [9]. Инсталляция сводится к созданию объектов в Kubernetes из манифестов.

Для использования CCM также понадобится:

  • указать [10] в манифесте идентификатор каталога (folder-id) Яндекс.Облака;
  • сервисный аккаунт для взаимодействия с API Яндекс.Облака. В манифесте Secret необходимо передать авторизованные ключи [11] от сервисного аккаунта. В документации описано [12], как создать сервисный аккаунт и получить ключи.

Будем рады обратной связи и новым issues [13], если столкнетесь с какими-то проблемами!

Итоги

Реализованный CCM мы используем в пяти Kubernetes-кластерах на протяжении двух последних недель и планируем расширить их число до 20 в ближайший месяц. Использовать CCM для больших и критических инсталляций K8s в настоящий момент не рекомендуем.

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

P.S.

Читайте также в нашем блоге:

Автор: Андрей Климентьев

Источник [15]


Сайт-источник PVSM.RU: https://www.pvsm.ru

Путь до страницы источника: https://www.pvsm.ru/open-source/348060

Ссылки в тексте:

[1] релизу CSI-драйвера: https://habr.com/ru/company/flant/blog/486190/

[2] Cloud Controller Manager: https://github.com/flant/yandex-cloud-controller-manager

[3] CCM: https://kubernetes.io/docs/concepts/architecture/cloud-controller/

[4] писали: https://habr.com/ru/company/flant/blog/465417/

[5] отдельный репозиторий: https://github.com/kubernetes/legacy-cloud-providers

[6] отдельный репозиторий: https://github.com/kubernetes/cloud-provider

[7] нужные Go-интерфейсы: https://github.com/kubernetes/cloud-provider/blob/release-1.17/cloud.go#L43

[8] готового(!) CCM: https://github.com/dlisin/yandex-cloud-controller-manager

[9] README: https://github.com/flant/yandex-cloud-controller-manager/blob/master/README.md

[10] указать: https://cloud.yandex.ru/docs/resource-manager/operations/folder/get-id

[11] передать авторизованные ключи: https://cloud.yandex.com/docs/iam/concepts/authorization/key

[12] описано: https://cloud.yandex.ru/docs/iam/quickstart-sa

[13] новым issues: https://github.com/flant/yandex-cloud-controller-manager/issues

[14] Готовить Kubernetes-кластер просто и удобно? Анонсируем addon-operator: https://habr.com/ru/company/flant/blog/455543/

[15] Источник: https://habr.com/ru/post/490356/?utm_source=habrahabr&utm_medium=rss&utm_campaign=490356