Łatwa obsługa skomplikowanych alertów. Albo historia stworzenia Balerter

Łatwa obsługa skomplikowanych alertów. Albo historia stworzenia Balerter

Wszyscy lubią alerty.

Oczywiście, znacznie lepiej otrzymać powiadomienie, gdy coś się wydarzyło (lub naprawiło), niż siedzieć, patrzeć na wykresy i szukać anomalii.

I stworzono wiele narzędzi do tego celu. Alertmanager z ekosystemu Prometheus i vmalert z grupy produktów VictoriaMetrics. Powiadomienia zabbix i alerty w Grafanie. Skrypty napisane w bash i boty Telegram, które okresowo sprawdzają jakiś URL i informują, jeśli coś jest nie tak. Naprawdę dużo tego.

My, w naszej firmie, również korzystaliśmy z różnych rozwiązań, aż napotkaliśmy na trudności, a właściwie niemożność stworzenia skomplikowanych, złożonych alertów. To, czego chcieliśmy, i co w końcu zrobiliśmy — poniżej. TLDR: Tak powstał projekt open source Balerter

Dość długo dobrze żyliśmy z alertami skonfigurowanymi w Grafanie. Tak, to nie jest najlepsza droga. Zawsze zaleca się używanie jakichś wyspecjalizowanych rozwiązań, takich jak Alertmanager. I my również wielokrotnie rozważaliśmy migrację. A potem, powoli, zapragnęliśmy więcej.

Powiedzieć, kiedy wykres spadł/wzrosł o XX% i znajduje się tam już N minut w porównaniu do poprzedniego okresu w M godzin? To wydaje się możliwe do zrealizowania w Grafanie lub Alertmanagerze, ale raczej nie jest to łatwe. (A może nawet nie jest możliwe, w tej chwili nie jestem pewien)

Wszytko staje się jeszcze bardziej skomplikowane, gdy decyzję o alercie należy podjąć na podstawie danych z różnych źródeł. Żywy przykład:

Sprawdzamy dane z dwóch baz Clickhouse, a następnie porównujemy je z niektórymi danymi z Postgresa i podejmujemy decyzję o alercie. Sygnalizować lub anulować.

Mieliśmy już sporo podobnych wymagań, byśmy zaczęli myśleć o naszym rozwiązaniu. I wtedy spróbowaliśmy stworzyć pierwszą listę wymagań/możliwości tego, jeszcze nie stworzonego, serwisu.

  • odnosić się do różnych źródeł danych. Na przykład, Prometheus, Clickhouse, Postgres.

  • wysyłać alerty do różnych kanałów — telegram, slack itp.

  • W trakcie rozmyślania stało się jasne, że chcemy nie deklaratywnego opisu, a możliwości pisania skryptów.

  • uruchamianie skryptów według harmonogramu.

  • łatwe aktualizowanie skryptów bez ponownego uruchamiania usługi.

  • możliwość rozszerzania funkcjonalności bez ponownego kompilowania usługi z kodu źródłowego.

To przykładowa lista, która prawdopodobnie nie jest bardzo dokładna. Niektóre punkty zmieniały się, inne umierały. Wszystko jak zwykle.

Właściwie tak właśnie rozpoczęła się historia Balerter.

Łatwa obsługa skomplikowanych alertów. Albo historia stworzenia Balerter

Postaram się krótko opisać, co ostatecznie udało się osiągnąć i jak to działa. (Tak, oczywiście, to nie jest koniec. Mamy wiele planów na rozwój produktu. Po prostu skupię się na dniu dzisiejszym)

Jak to działa?

Piszesz skrypt w Lua, w którym wyraźnie wysyłasz zapytania (do Prometheus, Clickhouse itd.). Otrzymujesz odpowiedzi i jakoś je przetwarzasz i porównujesz. Następnie włączasz/wyłączasz jakiś alert. Balerter sam wyśle powiadomienie do kanałów, które skonfigurowałeś (Email, telegram, slack itd.). Skrypt wykonuje się w ustalonych odstępach czasu. I… to właściwie wszystko)

Najlepiej pokazać na przykładzie:

-- @interval 10s
-- @name script1

local minRequestsRPS = 100

local log = require("log")
local ch1 = require("datasource.clickhouse.ch1")

local res, err = ch1.query("SELECT sum(requests) AS rps FROM some_table WHERE date = now()")
if err ~= nil then
    log.error("błąd zapytania 'ch1' w clickhouse: " .. err)
    return
end

local resultRPS = res[1].rps

if resultRPS < minResultRPS then
    alert.error("rps-min-limit", "Requests RPS są bardzo małe: " .. tostring(resultRPS))
else
    alert.success("rps-min-limit", "Requests RPS w porządku")
end 

Co tu się dzieje:

  • określamy, że ten skrypt powinien być wykonywany co 10 sekund

  • określamy nazwę skryptu (dla API, do wyświetlania w logach, do użycia w testach)

  • łączymy moduł do wyprowadzania logów

  • łączymy moduł do dostępu do clickhouse o nazwie ch1 (samo połączenie konfiguruje się w pliku konfiguracyjnym)

  • wysyłamy zapytanie do clickhouse

  • w przypadku błędu — wyprowadzamy komunikat do logu i wychodzimy

  • porównujemy wynik zapytania z stałą (w rzeczywistym przykładzie moglibyśmy tę wartość uzyskiwać, na przykład, z bazy Postgres)

  • włączamy lub wyłączamy alert o ID rps-min-limit

  • otrzymasz powiadomienie, jeśli status alertu się zmieni

Przykład jest dość prosty i zrozumiały. Jednak w rzeczywistości skrypty mogą być dosyć rozwlekłe i skomplikowane. Łatwo w nich się pogubić i popełnić błędy.

Dlatego pojawiła się logiczna chęć — możliwość napisania testów dla swoich skryptów. I w wersji v0.4.0 to się pojawiło.

Testowanie skryptów

Przykład testu dla naszego skryptu z powyższego przykładu:

-- @test script1
-- @name script1-test

test = require('test')

local resp = {
    {
        rps = 10
    }
} 

test.datasource('clickhouse.ch1').on('query', 'SELECT sum(requests) AS rps FROM some_table WHERE date = now()').response(resp)

test.alert().assertCalled('error', 'rps-min-limit', 'Requests RPS są bardzo małe: 10')
test.alert().assertNotCalled('success', 'rps-min-limit', 'Requests RPS w porządku')

Kroki:

  • określamy nazwę skryptu, dla którego napisano test

  • nazwa testu (do logów)

  • łączymy moduł do testowania

  • mówimy, jaki wynik należy zwrócić przy określonym zapytaniu do ClickHouse ch1

  • sprawdzamy, czy został wywołany alert (error) rps-min-limit z podanym komunikatem

  • sprawdzamy, czy alert rps-min-limit nie został wyłączony (success)

Co jeszcze potrafi Balerter?

Spróbuję poruszyć najważniejsze umiejętności Balerter, według mojej opinii. Szczegóły można zobaczyć na oficjalnej stronie https://balerter.com

  • pobierać dane z

    • clickhouse

    • postgres

    • mysql

    • prometheus

    • loki

  • wysyłać powiadomienia do kanałów

    • slack

    • telegram

    • syslog

    • notiify (powiadomienia UI na twoim komputerze)

    • email

    • discord

  • budować wykresy na podstawie twoich danych, przesyłać obrazy do kompatybilnego z S3 magazynu i dołączać je do powiadomień (Przykład z obrazkami)

  • umożliwia wymianę danych między skryptami — globalna pamięć Key/Value

  • pisanie własnych bibliotek w Lua i używanie ich w skryptach (domyślnie dostarczane są biblioteki lua do pracy z json, csv)

  • wysyłać zapytania HTTP z twoich skryptów (no i oczywiście odbierać odpowiedzi)

  • oferuje API (jeszcze nie tak funkcjonalne, jak byśmy chcieli)

  • eksportuje metryki w formacie Prometheus

A czego jeszcze chcielibyśmy się nauczyć?

Już widać, że użytkownicy i my chcemy mieć możliwość zarządzania uruchamianiem skryptów za pomocą składni cron. To będzie zrealizowane przed wersją v1.0.0

Chcielibyśmy wspierać więcej źródeł danych i kanałów dostarczania powiadomień. Na przykład komuś może zabraknąć MongoDB. Ktoś inny może potrzebować Elastic Search. Wysyłać SMS i/lub wykonywać połączenia telefoniczne na komórkę. Chcemy również móc pobierać skrypty nie tylko z plików, ale i na przykład z bazy danych. Ostatecznie chcielibyśmy, aby projekt miał bardziej przyjazną stronę oraz lepszą dokumentację.

Zawsze komuś czegoś brakuje) Tutaj liczymy na zapotrzebowanie społeczności, aby prawidłowo ustalić priorytety. I na pomoc społeczności, aby wszystko zrealizować.

Na zakończenie

Używamy Balerter mamy go już od jakiegoś czasu. Dziesiątki skryptów strzegą naszego spokoju. Mam nadzieję, że ta praca będzie przydatna także dla innych.

I zapraszamy do zgłaszania swoich Issue i PR.

Źródło: habr.com

Kup solidny hosting stron z ochroną przed DDoS, serwery VPS VDS 🔥 Kup solidny hosting stron z ochroną przed DDoS, serwery VPS VDS | ProHoster