Мониторинг (Prometheus)

Мониторинг (Prometheus) #

Сервис gateway отдаёт метрики в формате Prometheus по адресу GET /metrics. По ним можно строить графики нагрузки, времени ответа и доли ошибок, а также настраивать алерты.

Метрики считает только gateway - через него проходят все запросы к API, поэтому время ответа включает работу сервисов address, phone и name. Сами сервисы address, phone и name метрики не отдают.

Включение метрик #

Метрики включаются секцией [metrics] в файле gateway-config.toml (см. Установка ApiDQ приложения):

[metrics]
Enabled = true # метрики в формате Prometheus: GET /metrics

Если секции нет или Enabled = false, адрес /metrics отвечает 404, и метрики не собираются.

После изменения конфигурации перезапустите gateway:

cd ~/apidq
docker compose restart gateway

Проверьте, что метрики отдаются:

curl -s http://127.0.0.1:8080/metrics | grep '^http_'

Строки http_requests_total и http_request_duration_seconds появляются после первого запроса к API.

Список метрик #

МетрикаТипМеткиОписание
http_requests_totalcounterpath, method, statusКоличество обработанных HTTP-запросов
http_request_duration_secondshistogrampath, methodВремя обработки запроса в секундах
http_cache_requests_totalcounterpath, statusКоличество ответов из кеша (hit) и мимо кеша (miss)

Значения меток:

  • path - путь запроса в нижнем регистре, без параметров строки запроса, например /api/v1/clean/address;
  • method - HTTP-метод: GET, POST;
  • status у http_requests_total - HTTP-код ответа: 200, 400, 500, 503 и т.д.;
  • status у http_cache_requests_total - hit (ответ взят из кеша) или miss (ответ рассчитан заново).

У гистограммы http_request_duration_seconds стандартные границы интервалов Prometheus: 5 мс, 10 мс, 25 мс, 50 мс, 100 мс, 250 мс, 500 мс, 1 с, 2,5 с, 5 с, 10 с. Для каждой пары path + method она отдаёт ряды _bucket, _sum и _count.

http_cache_requests_total относится только к стандартизации адресов /api/v1/clean/address и появляется, если в сервисе address включено кеширование ответов. В стандартной конфигурации коробочной версии кеширование выключено, и этой метрики нет.

В учёт попадают все запросы к gateway, в том числе служебные /health и /metrics и запросы к несуществующим адресам (с кодом 404). Исключайте служебные пути в запросах к метрикам - см. примеры ниже.

Кроме того, /metrics отдаёт стандартные метрики Go-процесса gateway: go_* (горутины, память, сборка мусора) и process_* (CPU, память, открытые файлы).

Счётчики хранятся в памяти и обнуляются при перезапуске контейнера gateway. Функции rate() и increase() в Prometheus учитывают такой сброс автоматически.

Настройка Prometheus #

Добавьте в prometheus.yml задание сбора метрик со всех серверов ApiDQ. Если серверов несколько, перечислите каждый в targets:

scrape_configs:
  - job_name: apidq
    metrics_path: /metrics
    scrape_interval: 15s
    static_configs:
      - targets:
          - 192.168.0.20:8080 # ip сервера ApiDQ и порт gateway

Перезагрузите конфигурацию Prometheus и откройте страницу Status → Targets в его веб-интерфейсе: у задания apidq должно быть состояние UP.

Если Prometheus запущен в Docker на том же сервере, что и ApiDQ, укажите в targets адрес шлюза сети Docker - 172.17.0.1:8080. Адрес 127.0.0.1 внутри контейнера указывает на сам контейнер, а не на сервер.

Ограничение доступа к метрикам #

Адрес /metrics не требует авторизации и доступен всем, у кого есть доступ к порту gateway. Если порт gateway доступен из внешней сети, закройте /metrics для всех, кроме сервера Prometheus - например, на балансировщике или в межсетевом экране.

Пример для nginx, который проксирует запросы к gateway:

location ~* ^/metrics {
    allow 192.168.0.30; # ip сервера Prometheus
    deny all;
    proxy_pass http://127.0.0.1:8080;
}
gateway приводит путь запроса к нижнему регистру, поэтому /METRICS тоже отдаёт метрики. Используйте в правилах доступа сравнение без учёта регистра, как ~* в примере выше.

Ограничение доступа также защищает от роста числа рядов: каждый уникальный путь, в том числе несуществующий, создаёт в http_requests_total новый ряд, и сканирование сервера извне может породить их тысячи.

Примеры запросов PromQL #

Количество запросов в секунду по методам API:

sum by (path) (rate(http_requests_total{job="apidq", path!~"/health|/metrics"}[5m]))

Доля ответов с кодом 5xx:

sum(rate(http_requests_total{job="apidq", status=~"5..", path!~"/health|/metrics"}[5m]))
/
sum(rate(http_requests_total{job="apidq", path!~"/health|/metrics"}[5m]))

95-й перцентиль времени ответа по методам API:

histogram_quantile(0.95,
  sum by (path, le) (rate(http_request_duration_seconds_bucket{job="apidq", path!~"/health|/metrics"}[5m]))
)

Доля ответов стандартизации адресов из кеша:

sum(rate(http_cache_requests_total{job="apidq", status="hit"}[5m]))
/
sum(rate(http_cache_requests_total{job="apidq"}[5m]))

Готовность сервера ApiDQ проверяйте отдельно, по коду ответа GET /health (200 - все сервисы готовы, 503 - нет), например с помощью blackbox_exporter. Метрика up показывает только, что Prometheus смог получить /metrics от gateway, - при этом сервис address может быть ещё не готов принимать запросы.