ADG Оставить заявку
Блог DevOps 3 мин чтения

Istio 0.8 LTS: mTLS между микросервисами заработал, Kiali показал кто с кем разговаривает

Развернули Istio 0.8 в тестовом кластере Kubernetes. mTLS между сервисами поднялся без правок в коде, Kiali дал первую нормальную карту трафика.

Контекст момента

Istio 0.8 LTS (июнь 2018) - первый релиз с долгосрочной поддержкой, mTLS между сервисами, Mixer policy engine, Kiali как граф трафика

В конце июня вышел Istio 0.8 - первый релиз, который команда обозначила как LTS. До этого каждый минорный релиз мог что-нибудь сломать по-тихому, и в тестовые кластеры это ставили скорее ради интереса, чем с прицелом на что-то серьёзное. LTS-статус - это заявка на то, что API более или менее устаканились. Мы решили проверить на деле.

Тестовый кластер на managed-инфраструктуре - несколько сервисов, HTTP-трафик между ними, никакого шифрования на транспорте. Именно такой стенд удобен для проверки service mesh: есть что наблюдать, достаточно просто устроено чтобы понять что происходит.

Установка: Helm-чарт и куча CRD

Istio устанавливается через Helm-чарт из официального репозитория. Сам процесс несложный, но после helm install кластер обрастает примерно двадцатью CRD - VirtualService, DestinationRule, ServiceEntry, Policy, MeshPolicy и так далее. Это немного обескураживает: ты только что поставил инструмент, а у него уже больше абстракций чем у половины приложений в кластере.

Компоненты разворачиваются в namespace istio-system: Pilot (управляет конфигурацией Envoy), Mixer (policy и телеметрия), Citadel (выдаёт сертификаты для mTLS), Ingress Gateway. Плюс - в каждый под инжектируется sidecar-контейнер с Envoy-прокси. Для этого либо вешаешь аннотацию на namespace, либо включаешь автоматический webhook-инжектор.

Мы включили автоинжектор для тестового namespace. Пересоздали поды - и каждый из них получил второй контейнер istio-proxy. С точки зрения приложений ничего не изменилось: они по-прежнему слушают свои порты, Envoy перехватывает трафик через iptables-правила, которые init-контейнер прописывает при старте пода.

mTLS: включили - работает

Главное что хотелось проверить - взаимная аутентификация между сервисами без изменений в их коде. В Istio 0.8 это делается через два объекта: MeshPolicy (глобальная политика для всей сетки) и DestinationRule (правила для конкретного направления трафика).

Применили MeshPolicy с mtls: {} - включили mTLS в режиме STRICT для всех сервисов в сетке. Добавили DestinationRule с trafficPolicy.tls.mode: ISTIO_MUTUAL. После применения манифестов - HTTP-трафик между сервисами начал идти поверх TLS. В логах Envoy видно рукопожатие, в сертификатах - SPIFFE-идентификаторы (spiffe://cluster.local/ns/default/sa/...).

Это и есть главный практический результат: сервисы между собой теперь разговаривают по шифрованному каналу с взаимной проверкой. Разработчикам ничего переписывать не пришлось - ни в коде, ни в конфигурации приложений.

Один нюанс: если в кластере есть сервисы без sidecar (например, системные поды в kube-system), к ним STRICT mTLS не дотягивается и трафик туда идёт как раньше. Это ожидаемо, но надо держать в голове при проверке политик.

Kiali: наконец-то нормальная карта

Kiali - это UI для Istio, появился примерно в то же время что и 0.8. Устанавливается отдельно, подключается к Prometheus (куда Mixer сливает телеметрию) и рисует граф трафика: какой сервис с каким разговаривает, сколько запросов в секунду, какой процент ошибок на каждом ребре.

До этого у нас было ощущение что мы знаем архитектуру - но это было знание из документации и из голов разработчиков, не из реального трафика. Kiali показал несколько неожиданных вещей: один сервис стучался к другому заметно чаще чем предполагалось, и один из сервисов периодически получал ответы с 5xx от зависимости, которую мы считали стабильной.

Это не то что кто-то скрывал - просто без инструмента наблюдаемости такие вещи тихо живут в кластере и всплывают только когда уже что-то сломалось.

[svc-api] ----> [svc-catalog]  200 OK, ~40 rps
[svc-api] ----> [svc-auth]     200 OK, ~15 rps
[svc-worker] -> [svc-catalog]  200 OK / 503 ~2%, ~8 rps  <-- вот это было сюрпризом

Граф обновляется в реальном времени. Можно кликнуть на ребро и посмотреть детали: latency по перцентилям, распределение статус-кодов. Для первичного понимания того что реально происходит в кластере - очень удобно.

Что не понравилось

Mixer - самое тяжёлое место. Каждый запрос через Envoy синхронно ходит в Mixer за policy-решением и отправляет телеметрию. При нашей нагрузке это добавляет задержку, которую на тестовом стенде мы заметили, но не измерили систематически. При высоком rps Mixer может стать узким местом - это известная проблема 0.8, и обходится она кэшированием на стороне Envoy, которое включается отдельно.

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

Ресурсов sidecar потребляет заметно: каждый istio-proxy ест несколько десятков мегабайт памяти в покое. На кластере из десятков подов это начинает складываться в заметные суммарные накладные расходы.

Итог

mTLS заработал без правок в коде сервисов - это честный результат, ради которого и стоило пробовать. Kiali дал то чего не хватало: реальную карту трафика, а не нарисованную вручную в Confluence. Теперь понятно кто с кем и как часто разговаривает.

В продакшн пока не тащим - смотрим на поведение Mixer под нагрузкой и разбираемся с политиками. Но тестовый стенд с Istio 0.8 остаётся запущенным, это уже не эксперимент ради галочки.

Контакт

Нужна такая же инженерная работа?

Опишите задачу и контекст. Ответим в течение рабочего дня, при необходимости подпишем NDA.