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

Grafana 11.1 и Scenes API: перекраиваем инфра-дашборды под динамические переменные

Grafana 11.1 стабилизировала Scenes API. Перевели ключевые дашборды инфраструктуры на Scenes - сегмент/хост как переменные сократили панели вдвое при той же детализации.

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

Grafana 11.1 выпустила стабильный Scenes API для динамических дашбордов и улучшенный Alerting v2 с поддержкой группировки правил

Grafana 11.1 вышла в середине июля, и главное, что нас в ней интересовало - статус Scenes API. В 10.3 он уже был, но с кучей шероховатостей и пометкой «попробовать можно, но в прод не надо». В 11.1 команда Grafana Labs объявила его готовым к использованию без оговорок. Мы восприняли это как приглашение разобраться с проблемой, которая давно раздражала в наших инфра-дашбордах.

Проблема, которую решал Scenes API

У нас в dwh-bi несколько инфраструктурных стендов: разные сегменты сети, десятки хостов в каждом, перекрывающиеся метрики от Prometheus и Zabbix. Классический подход - создать один дашборд на сегмент и внутри него строки с панелями по хостам. Звучит нормально, пока хостов пять. Когда их двадцать, дашборд превращается в полосу прокрутки длиной с экран и весит при загрузке соответственно: браузер сначала фетчит данные по всем хостам сразу, рендерит всё разом, и первые секунды - просто белый экран.

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

Стандартные template variables в Grafana эту проблему решают частично. Переменная host работает, но панели всё равно статичны: если хочешь показать одну и ту же метрику для выбранного хоста с нужным layout-ом, приходится либо дублировать панели с фильтрацией по переменной, либо городить трансформации. Ни то ни другое не масштабируется.

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

Что мы переводили и как

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

Scenes API предполагает написание кода - дашборд описывается на TypeScript через библиотеку @grafana/scenes. Это порог входа, которого в классическом Grafana не было: раньше всё делалось кликами в UI. С одной стороны, это неудобно. С другой - дашборд наконец живёт в git, версионируется нормально и деплоится через CI, а не «кто-то поменял руками и забыл».

Структура получилась такая: верхний уровень - SceneApp с двумя страницами (сегменты и детализация хоста). На уровне страницы - VariableSet с переменными segment и host, где host зависит от выбранного segment через Prometheus label values. Внутри - SceneFlexLayout с SceneRepeater, который динамически строит строки панелей под каждый хост в сегменте.

Самая нетривиальная часть - SceneRepeater для строк хостов. В классическом Grafana repeat row работает, но плохо взаимодействует со сложными layout-ами: строки просто стекаются вертикально, без возможности настроить grid внутри каждой строки по-своему. В Scenes это решается нормально: каждый «инстанс» repeater-а получает свой SceneFlexLayout с нужным набором панелей.

Что получилось в цифрах

Точные цифры не приведём - они разные для каждого дашборда и зависят от количества хостов в сегменте. Но порядок такой: для обзорного дашборда сегментов количество отображаемых панелей при выборе конкретного сегмента сократилось примерно вдвое по сравнению со старым вариантом, где все хосты всех сегментов лежали в одном JSON. Время первой загрузки - ощутимо меньше, потому что Grafana теперь фетчит данные только для видимых панелей, а не для всего дашборда целиком.

Детализация при этом не пострадала. Скорее наоборот: раньше в одном дашборде было невозможно показать глубокий разрез по конкретному хосту без отдельного дашборда-листа. Теперь переход «сегмент -> хост» работает через drill-down внутри одного SceneApp.

Alerting v2 в 11.1

Из других новинок релиза - улучшения в Alerting v2. Главное изменение: группировка правил оповещений по папкам, аналогично тому как организованы дашборды. Раньше все alert rules лежали в одной плоской структуре Grafana Alerting, и при числе правил больше нескольких десятков это превращалось в свалку.

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

Ещё одно изменение - улучшенный интерфейс создания правил с предпросмотром результатов запроса прямо в форме. Раньше надо было отдельно идти в Explore, проверять запрос, копировать в alert rule. Теперь - в одном экране.

Что пока не гладко

Сборка Scenes-дашбордов через TypeScript требует локального окружения для разработки и плагинного механизма Grafana для деплоя. Это не rocket science, но инфраструктура для этого нужна: Node.js, сборка плагина, деплой в Grafana. Для команды, которая привыкла редактировать дашборды в UI кнопками, порог высокий.

Документация по Scenes API на момент 11.1 ещё неполная. Часть поведения пришлось выяснять через исходники библиотеки и примеры в репозитории Grafana Labs. Не критично, но время съедает.

SceneRepeater в текущей реализации не поддерживает произвольную вложенность - repeater внутри repeater не работает так, как ожидаешь. Для большинства задач это не проблема, но один кейс (хосты внутри сервисов внутри сегментов) нам пришлось обойти плоским списком с фильтрацией.

Где сейчас

Три дашборда переведены, работают в продуктиве. Остальные - пока на старом подходе: Scenes API оправдывает себя там, где дашборд действительно динамический и хостов много. Для статичного дашборда с тремя-четырьмя панелями городить TypeScript-плагин - избыточно.

Следующее, что хотим попробовать - Scenes drill-down pages для аномалий: когда алерт сработал, переход должен сразу открывать контекстный вид по конкретному хосту и временному окну. В Scenes это теоретически делается через SceneAppPage с параметрами в URL - посмотрим, как это ляжет на нашу топологию.

Контакт

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

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