Язык запросов PromQL: синтаксис, базовые выражения и примеры
PromQL - центральный механизм взаимодействия с данными временных рядов в Prometheus и его экосистеме. Этот язык проектирован для гибкого извлечения сведений из множества метрик, их агрегации по различным размерностям и последующей визуализации в дашбордах или инцидент-менеджменте. В рамках курса мы сфокусируемся на синтаксисе, базовых выражениях и практических сценариях, которые позволяют инженерам данных и DevOps строить аналитические запросы, обеспечивать мониторинг производительности и выявлять закономерности в поведении систем.
PromQL сочетает в себе понятия instant и range вектора, поддерживает диапазонные окна, агрегации по лейблам и сложные паттерны соединения данных. В отличие от полноценного SQL, PromQL оптимизирован для потоковых данных: он работает над временными рядами, где каждый ряд идентифицируется набором ярко заданных лейблов, а время - непрерывная ось. Эффективная работа PromQL достигается через продуманное проектирование метрик, выбор режимов агрегации и стратегий хранения, включая запись правил (recording rules) и использование продвинутых бекендов для длинной истории (например, Thanos, Cortex). Важно помнить: PromQL - это не просто язык запросов, а средство моделирования реальных процессов мониторинга и анализа устойчивости систем.
-
В этой главе акцент делается на архитектурном контексте, алгоритмах выборки и интеграциях, а также на типичных кодовых паттернах запросов, которые применяются в больших развертываниях.
-
Приведённые примеры ориентированы на реальные кейсы и демонстрируют принципы формирования эффективных запросов, избегая чрезмерной абстракции и оставаясь применимыми к промышленным системам мониторинга.
-
Краткое содержание главы
-
Архитектура и концепции PromQL: как Prometheus оценивает запросы и как это вписывается в стек мониторинга
-
Синтаксис, операторы и базовые выражения: селекторы, диапазонные окна, агрегации и функции
-
Аналитические паттерны и практики: соединения метрик, сравнение значений во времени и временные вычисления
-
Практики интеграции и хранения: производительность запросов, управление кардинальностью и работа с долговременным хранением
Вводный обзор PromQL: концепции и архитектурное место Prometheus
PromQL выполняет роль слоя аналитической выборки внутри Prometheus. Когда пользователь отправляет запрос через API Prometheus или через интеграции (Grafana, Alertmanager и пр.), движок PromQL интерпретирует выражение, собирает данные с локального TSDB и возвращает результат. Важнейшие концепции:
- Вектор Instant: результатом является множество серий с одним временным моментом времени. Каждая серия определяется уникальным сочетанием лейблов.
- Вектор Диапазон (Range Vector): серия, возвращающая временной ряд за указанный интервал. Диапазонный вектор позволяет вычислять динамические показатели вроде rate, avg_over_time и quantile_over_time.
- Селекторы метрик: метрика по имени с набором правил выбора лейблов, например, http_requests_total{job="web", env!="prod"}.
- Операторы и функции: арифметика, логические операторы, набор функций для агрегаций и статистических вычислений над временными рядами.
- Архитектура хранения и запросов: Prometheus собирает данные, хранит их в собственном TSDB, предоставляет API для запросов, поддерживает remote_write и remote_read, а также интегрируется с внешними хранителями через слоя Thanos, Cortex и Victo riaMetrics.
- Практика проектирования: выбор метрик, нивелирование высокой кардинальности, агрегации на уровне PromQL через sum by/avg by, и применение правил записи для снижения сложности запросов в дашбордах и оповещениях.
Понимание архитектуры PromQL важно, поскольку многие вопросы производительности зависят от того, как данные индексируются и как выполняются агрегации. Прежде чем писать сложные запросы, рекомендуется помнить: чем шире набор лейблов и чем чаще вы запрашиваете длинные диапазоны, тем выше требования к памяти и времени отклика сервера. В этом контексте целесообразно использовать механизмыRecording Rules и ограничение cardinality посредством корректной стратегии номенклатуры метрик и relabeling.
Синтаксис PromQL: выражения, операторы и временные окна
PromQL поддерживает два основных типа выражений: instant vectors и range vectors. Instant выражает состояния в конкретный момент времени, range - значения во времени за заданный период. Селекторы позволяют выбирать метрики по имени и лейблам; операторы применяются к векторам для выполнения арифметических и логических операций.
Ключевые элементы синтаксиса:
- Селекторы метрик и лейблов: metric_name{label1="value1", label2!="value2"}.
- Точные и частично совпадающие сопоставления; условия ~= и !~ применяются для регулярных выражений.
- Диапазоны: metric_name[5m]** - диапазон 5 минут для диапазонного вектора.
- Инстантные и диапазонные функции: rate(http_requests_total[5m]), avg_over_time(cpu_seconds_total[1h]).
- Агрегации по лейблам: sum by (instance) (rate(http_requests_total[5m])), max_over_time(memory_usage_bytes[10m]).
- Пространственные и временные операторы: +, -, *, /; on, ignoring, bool, and, unless, group_left, group_right - для управления соответствием лейблов между операндами.
Важно понимать различие между rate и irate:
- rate вычисляет среднюю скорость изменения значения за окно и возвращает плавную кривую. Этот подход устойчив к дрейфу и шуму.
- irate - мгновенную скорость изменения на основе последних двух точек в окне и полезен на очень частых данных, но может быть более шумным.
Ниже приведены примеры запросов, иллюстрирующие базовые принципы.
rate(http_requests_total{job="web"}[5m])sum by (instance) (rate(http_requests_total{job="web"}[5m]))avg_over_time(http_request_duration_seconds_sum[1h])
max_over_time(cpu_seconds_total{mode="idle"}[15m])quantile_over_time(0.95, rate(http_requests_total[5m])[1h])
На практике полезно комбинировать селекторы и агрегации для получения целевых показателей. Рассмотрим типовой сценарий: вы хотите получить скорость запросов к каждому экземпляру веб-приложения за последние 5 минут и суммарную величину по всем экземплярам. Запрос будет выглядеть так:
sum by (instance) (rate(http_requests_total{job="web"}[5m]))Если требуется сопоставить задержку ответа с доступностью сервиса по тем же экземплярам, можно объединить два набора метрик через бинарные операторы и директивы on/ignoring:
sum by (instance) (rate(http_requests_total{job="web"}[5m]))
/
on(instance) ignoring(instance)
group_left
sum by (instance) (http_response_time_seconds_sum{job="web"}[5m])Этот паттерн иллюстрирует как PromQL позволяет “соединять” метрики с разными наборами лейблов, сохраняя при этом корректность агрегаций. Важной особенностью является возможность управления соответствием лейблов через on/ignoring, что позволяет гибко контролировать, какие лейблы участвуют в операторе соединения.
Еще один важный момент - обработка отсутствующих значений. Вывод absent() позволяет корректно обозначать случаи, когда метрика не была сгенерирована в заданный момент времени:
absent(up{job="web"})Для корректной интерпретации отсутствия можно комбинировать с существующими метриками и использовать операторы bool или unless, чтобы избежать ложноположительных сигналов в алертах.
Базовые выражения и агрегации: выбор метрик, фильтры, агрегации по временным окнам
Базовые практики в PromQL начинаются с умелого выбора метрик и агрегирования. В большинстве сценариев задача состоит в том, чтобы превратить поток отдельных временных рядов в понятную метрику верхнего уровня, например суммарную нагрузку по сервису или задержку по окружению.
-
Выбор метрик и фильтрация по лейблам. Примеры:
http_requests_total{job="api", environment!="staging"} -
Агрегации по лейблам. Пример, суммирование по сервису:
sum by (service) (rate(http_requests_total{job="api"}[5m]))
- Подсчёт событий и агрегированные статистики во времени:
count_over_time(http_requests_total[1h])
sum_over_time(http_request_duration_seconds_sum[1h])
-
Временные функции для анализа драйверов задержки:
histogram_quantile(0.95, rate(http_request_duration_seconds_bucket[5m]))
-
Простейшее вычисление загрузки CPU по времени:
avg(rate(node_cpu_seconds_total{mode="idle"}[5m])) -
Примеры рабочих паттернов:
- Мониторинг доступности сервиса:
avg_over_time(up{job="gateway"}[5m])
- Мониторинг доступности сервиса:
-
Суммарная нагрузка по кластерам:
sum by(cluster) (rate(request_total{job="gateway"}[5m]))Эти выражения иллюстрируют типовой набор операций: выбор по имени метрики, фильтрация по лейблам, агрегация по нужным лейблам и вычисление темпов изменения во времени. В реальных системах часто применяются комбинации rate/irate в контексте длительных окон, чтобы отображать устойчивые тренды, а не случайные колебания.
Аналитические паттерны в PromQL: расчеты, временные сопоставления и сравнения
PromQL поддерживает богатый набор аналитических паттернов, которые полезны для мониторинга производительности, предупреждений и корневой причины. Основные принципы:
- Ансамбль по лейблам (aggregate by). Выполнение агрегаций по определённым лейблам позволяет выявлять закономерности внутри служб, зон, экземпляров и пр.
- Сопоставление и бинарные операции. Использование бинарных операций (например, деление, умножение) совместно с директивами on/ignoring и group_left/group_right позволяет «совмещать» данные из разных источников, не объединяя лишние лейблы.
- Функции над диапазонами. Функции (rate, avg_over_time, max_over_time, quantile_over_time) позволяют получить конъюнктурные характеристики по времени: темпы, средние значения, верхние квартильные показатели и т.д.
- quantile_over_time. Применимо к данным, агрегированным по лейблам; позволяет рассчитывать квантиль по распределению, полученному из данных о времени обработки или задержке.
-absent и presence patterns. Выявление отсутствия метрик полезно для обнаружения дефектов цепочки поставки метрик или агрегационных правил.
Практические примеры:
-
Расчет 95-й перцентели задержек по сервисам за последний час:
quantile_over_time(0.95, rate(http_request_duration_seconds_sum{job="api"}[5m])[1h]) -
Сравнение доступности двух наборов сервисов в одном окне и сигнализация, если один из них падает ниже другого:
avg by (service) (rate(http_requests_total{env="prod"}[5m])) - avg by (service) (rate(http_requests_total{env="prod-canary"}[5m])) -
Пример с использованием group_left для сопоставления latency и throughput по одному лейблу (instance):
rate(http_request_duration_seconds_sum[5m]) / on(instance) group_left rate(http_requests_total[5m])
В сложных сценариях промQL может обрабатывать миллионы серий. Поэтому для систем с высоким объемом данных рекомендуется применять стратегию предварительной агрегации через recording rules, чтобы снизить стоимость вычислений на уровне запросов и упростить dashboard-логики.
Интеграции и практики: хранение, high cardinality, мониторинг производительности и примеры
Эффективный промQL-подход требует согласованной стратегии проектирования метрик и использования возможностей экосистемы Prometheus. В контексте архитектуры важно рассмотреть как Prometheus взаимодействует с хранилищем данных, как организованы remote чтение/запись и какие варианты для долговременного хранения применимы в крупных средах.
- Архитектура хранения. Прометей хранит данные на местном TSDB-слое и обеспечивает быстрый доступ к свежим данным. Для долгосрочного хранения используйте внешние решения, такие как Thanos или Cortex, которые позволяют агрегировать данные из множества инстансов, обеспечивать глобальные запросы и долговременное хранение.
- Кардинальность и дизайн метрик. Высокая кардинальность (много уникальных значений лейблов) может привести к перерасходу памяти и ухудшению производительности. Практики:
- ограничение числа и значения лейблов, особенно в метрикахomain класса, в формате, который поддерживает агрегируемость;
- использование relabel_config для удаления или переназначения лейблов в процессе сборки;
- создание recording rules для пред-агрегаций, чтобы снизить нагрузку на запросы в PromQL.
- Интеграции с инструментами визуализации и алертинга. Grafana широко применяется как фронтенд для Prometheus и его экосистемы. Использование Grafana Data Source Prometheus позволяет параметризовать запросы, строить дашборды и создавать алерты на основе сохранённых выражений.
- Практики по производительности. Для сложных запросов и больших наборов серий применяйте:
- ограничение времени и суточных окон;
- пред-агрегации через recording rules;
- использование эффективных функций над диапазонами (quantile_over_time, rate и т.д.) с учётом размера окна;
- тестирование запросов в среде разработки и использование профилирования через Prometheus-панели или внешние инструменты мониторинга.
Пример записи правила (recording rule) для снижения нагрузки на дашборды и алерты:
groups:
- **name**: http_requests_rules
rules:
- **record**: job:http_requests:rate5m
expr: rate(http_requests_total[5m])
labels:
source: "prometheus"
Такое правило создаёт новый временной ряд, который затем можно использовать в дашбордах и алертах без повторного вычисления исходного выражения на каждом запросе.
Что касается интеграций с конкретными продуктами, в реальных системах часто встречаются:
- Thanos - обеспечивает глобальные запросы, долговременное хранение и кэширование, снижая ограничения локального Prometheus.
- VictoriaMetrics - сервер мониторинга и хранения, который поддерживает PromQL и обеспечивает высокую производительность на больших наборах данных.
Использование одного из этих решений зависит от масштаба инфраструктуры, требований к федерации данных и потребностей в долговременном хранении.
Высокая кардинальность - один из самых критичных факторов для проектирования в PromQL. Подходы включают:
- перенос части лейбла с высокими изменениями в именование или удаление;
- сокращение количества лейблов в именах метрик;
- агрегации в местном слое Prometheus и использование recording rules для консолидации;
- использование внешнего хранилища для старой истории данных, чтобы сохранить доступ к данным без перегрузки локального сервера.
Key takeaways
- PromQL - мощный язык запросов для анализа временных рядов в Prometheus, поддерживающий instant и range вектора, селекторы и агрегации по лейблам.
- Различайте instant vectors и range vectors, чтобы правильно строить запросы с rate, avg_over_time и quantile_over_time.
- Эффективная работа с большими данными требует использования recording rules, контроля кардинальности и разумного проектирования метрик.
- Базовые паттерны включают агрегацию по нужным лейблам, бинарные операции для сопоставления данных и корректное управление отсутствием данных через absent/presence.
- Для масштабируемых окружений применяйте внешние хранилища (Thanos, Cortex) и продуманную стратегию хранения данных.
- Grafana + Prometheus - классический стек для визуализации и мониторинга; используйте дашборды и алертинг на основе промQL-выражений.
- Тестируйте запросы на реальных сценариях, учитывая задержки, частоту сэмплов и объем серий, чтобы избежать перегрузки сервера.
FAQ
- Что такое instant vector и range vector в PromQL, и зачем они нужны?
Instant vector описывает набор временных рядов на конкретный момент времени. Range vector - это набор значений того же ряда за указанный диапазон времени. Разница критична: rate и другие функции работают именно с range vectors, а визуализация и оповещения часто используют instant vectors. Понимание различий позволяет формировать корректные выражения и не допускать ошибок в агрегациях.
- Чем отличается rate от irate и когда использовать каждую из функций?
rate рассчитывает среднюю скорость изменения за заданное окно и является плавной, устойчивой к шуму. Используйте rate для аналитики по умеренным частотам обновления и когда нужен стабильный тренд. irate вычисляет скорость за последнюю пару точек и подходит для очень частых измерений, где важна мгновенная реакция на изменения, хотя может быть более подверженным шуму. В практике часто применяют rate для дашбордов и алертинга, а irate - для быстрого выявления резких изменений.
- Как правильно агрегировать данные по лейблам без потери нужной granularity?
Используйте агрегаты sum by, avg by и т.д. по нужным лейблам, чтобы сохранить важные контексты (service, instance, region) и избежать спайк-эффектов. Применяйте relabeling на этапе сбора метрик для удаления лишних лейблов или нормализации имен, снижая кардинальность и улучшая производительность.
- Как работать с отсутствием данных в PromQL?
absent() позволяет определить случаи, когда определённая метрика не была сгенерирована в заданный момент, что полезно для предупреждений о деградации цепочек метрик. Комбинирование absent() с другими выражениями помогает идентифицировать пропуски данных и действия по устранению неисправностей.
- Какие практики помогают управлять высокой кардинальностью метрик?
Ограничивайте число лейблов в именах метрик, используйте relabel_configs для удаления ненужных лейблов на этапе сбора, создавайте recording rules для снижения количества вычисляемых выражений в запросах, и применяйте долговременное хранение через Thanos/Cortex для исторических данных, чтобы не перегружать локальные инстансы Prometheus.
- Как строить кросс-сервисные запросы с использованием бинарных операторов?
PromQL поддерживает бинарные операции между векторами, что позволяет, например, сравнивать нагрузку между двумя сервисами или объединять метрики с разными лейблами через on/ignoring и group_left/group_right. Важно корректно выбрать лейблы, чтобы не создавать ненужных пересечений и не получить неверные результаты.
- Что нужно учитывать при оценке производительности PromQL запросов?
Время выполнения запросов растет с числом серий, размером окон и количеством агрегаций. Рекомендуется:
- использовать recording rules для частых или тяжёлых выражений;
- оптимизировать диапазоны, избегать слишком долгих окон без необходимости;
- профилировать запросы и тестировать на тестовых кластерах;
- рассмотреть внедрение внешнего хранилища для долговременного хранения и федерации данных.
- Какие сценарии подходят для использования Thanos или Cortex в связке с Prometheus?
Thanos и Cortex обеспечивают глобальные запросы и долговременное хранение, что особенно полезно в кластерах с множеством Prometheus-инстансов и необходимостью анализа across-cluster данных. Они позволяют масштабировать хранение и обработки запросов и поддерживают единый слой мониторинга. Выбор зависит от требований к консолидации данных и инфраструктурной сложности.
- Как внедрять и тестировать recording rules для продакшена?
Recording rules позволяют преформировать часто используемые выражения в новые временные серии, которые кэшируются и используются повторно. Это существенно снижает нагрузку на кобор Prometheus. В тестовой среде рекомендуется поэтапно внедрять правила, проверять их влияние на производительность, тестировать корректность агрегаций и убедиться, что правила не приводят к переполнению памяти из-за резкого роста количества серий.
- Какие базовые принципы следует соблюдать при проектировании PromQL-выражений для больших развёртываний?
- минимизируйте число сканируемых серий за счет фокусирования на нужных лейблах;
- применяйте rate/quantile_over_time только там, где это имеет смысл;
- используйте recording rules для часто используемых выражений;
- планируйте хранение и ретеншн через внешние хранилища;
- тестируйте выражения в безопасной среде и постепенно переносите в продакшн.
Эта глава охватывает основы PromQL, а также архитектурные и практические аспекты использования языка запросов в крупных системах мониторинга. В следующих главах будет рассмотрено углубление по агрегациям, вычислению метрик, анализу временных рядов и стратегиям оптимизации хранения, включая работу с high cardinality и построение эффективных аналитических запросов.



