Создание пользовательских метрик Prometheus в Golang и отправка оповещений в Slack с Grafana



Книга Создание пользовательских метрик Prometheus в Golang и отправка оповещений в Slack с Grafana


Цели



  • Создание пользовательских метрик Prometheus в Go.

  • Визуализация пользовательских метрик в Grafana.

  • Создать веб-хук Slack.

  • Создать оповещение в Grafana.

  • Отправить в Slack сообщение с оповещением.


Создание пользовательских метрик Prometheus



  • prometheus.go:


package metrics

import (
"github.com/prometheus/client_golang/prometheus"
)

var (
HttpRequestCountWithPath = prometheus.NewCounterVec(
prometheus.CounterOpts{
Name: "http_requests_total_with_path",
Help: "Number of HTTP requests by path.",
},
[]string{"url"},
)

// PROMQL => rate(http_request_duration_seconds_sum{}[5m]) / rate(http_request_duration_seconds_count{}[5m])
HttpRequestDuration = prometheus.NewHistogramVec(
prometheus.HistogramOpts{
Name: "http_request_duration_seconds",
Help: "Response time of HTTP request.",
},
[]string{"path"},
)
)

func init() {
prometheus.MustRegister(HttpRequestCountWithPath)
prometheus.MustRegister(HttpRequestDuration)
}

HttpRequestCountWithPath: этой метрикой показывается, сколько HTTP-запросов отправляется по одному и тому же пути.


HttpRequestDuration: этой метрикой показывается время ответа HTTP-запроса.


prometheus.MustRegister() вызывается для регистрации метрик с Prometheus. Регистрация необходима для извлечения этих метрик с помощью Prometheus.


Использование метрик в промежуточном ПО



  • middleware.go:


/*
Регистрируем на New Relic все HTTP-запросы и ответы.
Генерируется пользовательская метрика счетчика для Prometheus. Используются путь HTTP-запроса и HTTP-метод.
*/
func (m middleware) LogMiddleware(ctx *gin.Context) {
reqMethodAndPath := fmt.Sprintf("[%s] %s", ctx.Request.Method, ctx.FullPath())

// Длительность ответа на HTTP-запрос
timer := prometheus.NewTimer(metrics.HttpRequestDuration.WithLabelValues(reqMethodAndPath))
defer timer.ObserveDuration()

var responseBody = logging.HandleResponseBody(ctx.Writer)
var requestBody = logging.HandleRequestBody(ctx.Request)
requestId := uuid.NewString()

if hub := sentrygin.GetHubFromContext(ctx); hub != nil {
hub.Scope().SetTag("requestId", requestId)
ctx.Writer = responseBody
}
ctx.Next()

statusCode := ctx.Writer.Status()
// Тот же счетчик пути HTTP-запроса
metrics.HttpRequestCountWithPath.With(prometheus.Labels{"url": reqMethodAndPath}).Inc()
logMessage := logging.FormatRequestAndResponse(statusCode, ctx.Request, responseBody.Body.String(), requestId, requestBody)

if logMessage != "" {
if isSuccessStatusCode(statusCode) {
m.logger.Info(logMessage)
} else {
m.logger.Error(logMessage)
}
}
}

func isSuccessStatusCode(statusCode int) bool {
switch statusCode {
case http.StatusOK, http.StatusCreated, http.StatusAccepted, http.StatusNoContent:
return true
default:
return false
}
}

Пользовательские метрики в Grafana




PromQl => my_http_requests_total_with_path





PromQl =>




rate(http_request_duration_seconds_sum{}[5m]) 

rate(http_request_duration_seconds_count{}[5m])



Разделив показатель суммы на показатель счетчика, получаем среднюю продолжительность каждого запроса за последние пять минут.


Создание веб-хука Slack




У меня уже имеются бот и веб-хук Slack, которым на канал #random в Slack отправляется сообщение.


Создание оповещения в Grafana


По этой ссылке создаем контактную точку оповещения с URL-адресом веб-хука Slack:




Если среднее время ответа на HTTP-запрос больше 0,3 мс, на канал Slack отправляется сообщение с оповещением, это последние пять минут в этом запросе.


Сохраним правило и обратим внимание на состояние работоспособности:



Похоже, работоспособность в норме.


Отправка HTTP-запроса со временем ожидания



Этой строкой время отклика задерживается.


В конечную точку GetUserById отправлено слишком много запросов.



  • Время отклика  —  более 0,5 мс.

  • Среднее время отклика увеличилось.

  • Появляется тег запуска.




  • Похоже, метрика нерабочая.




  • Оповещение активировалось, и на канал Slack отправлено сообщение.




Сообщение с оповещением настраивается добавлением аннотаций или указанием пользователей.



Вот репозиторий на GitHub.



206   0  

Comments

    Ничего не найдено.