Metrikspeicher: Wie wir von Graphite+Whisper zu Graphite+ClickHouse gewechselt sind

Hallo alle! In seinem letzter Artikel Ich habe über die Organisation eines modularen Überwachungssystems für eine Microservice-Architektur geschrieben. Nichts steht still, unser Projekt wächst stetig und damit auch die Anzahl der gespeicherten Metriken. Wie wir den Übergang von Graphite + Whisper zu Graphite + ClickHouse unter Hochlastbedingungen organisiert haben, lesen Sie über die Erwartungen daran und die Ergebnisse der Migration unter dem Schnitt.

Metrikspeicher: Wie wir von Graphite+Whisper zu Graphite+ClickHouse gewechselt sind

Bevor ich Ihnen erzähle, wie wir den Übergang von der Speicherung von Metriken in Graphite + Whisper zu Graphite + ClickHouse organisiert haben, möchte ich Sie über die Gründe für eine solche Entscheidung und über die Nachteile von Whisper informieren, mit denen wir lange gelebt haben.

Graphite+Whisper-Probleme

1. Hohe Belastung des Festplattensubsystems

Zum Zeitpunkt der Umstellung flogen etwa 1.5 Millionen Messwerte pro Minute zu uns. Bei diesem Ablauf betrug die Festplattenauslastung auf den Servern etwa 30 %. Im Allgemeinen war es durchaus akzeptabel - alles funktionierte stabil, wurde schnell geschrieben, schnell gelesen ... Bis eines der Entwicklungsteams eine neue Funktion einführte und anfing, uns 10 Millionen Metriken pro Minute zu senden. Zu diesem Zeitpunkt wurde das Festplatten-Subsystem gestrafft und wir konnten eine 100-prozentige Auslastung feststellen. Das Problem wurde schnell gelöst, der Bodensatz blieb jedoch zurück.

2. Mangelnde Replikation und Konsistenz

Höchstwahrscheinlich haben wir, wie jeder, der Graphite + Whisper verwendet/verwendet hat, denselben Messwertstrom gleichzeitig auf mehrere Graphite-Server übertragen, um Fehlertoleranz zu schaffen. Und dabei gab es keine besonderen Probleme – bis einer der Server aus irgendeinem Grund ausfiel. Manchmal gelang es uns, den ausgefallenen Server schnell genug hochzufahren, und Carbon-C-Relay schaffte es, ihn mit Metriken aus seinem Cache zu füllen, und manchmal nicht. Und dann gab es eine Lücke in den Metriken, die wir mit rsync geschlossen haben. Das Verfahren war ziemlich langwierig. Nur dadurch gerettet, dass dies sehr selten vorkam. Wir haben auch regelmäßig einen zufälligen Satz von Metriken genommen und sie mit anderen ähnlichen Metriken auf benachbarten Knoten des Clusters verglichen. In etwa 5 % der Fälle unterschieden sich mehrere Werte, was uns nicht sehr gefreut hat.

3. Großer Platzbedarf

Da wir in Graphite nicht nur Infrastruktur-, sondern auch Geschäftsmetriken (und jetzt auch Metriken von Kubernetes) schreiben, kommt es häufig vor, dass die Metrik nur wenige Werte enthält und die .wsp-Datei erstellt wird Berücksichtigt den gesamten Aufbewahrungszeitraum und belegt einen vorab zugewiesenen Speicherplatz, der bei uns etwa 2 MB betrug. Das Problem wird durch die Tatsache verschärft, dass es im Laufe der Zeit viele solcher Dateien gibt und das Lesen leerer Punkte beim Erstellen von Berichten viel Zeit und Ressourcen kostet.

Ich möchte sofort darauf hinweisen, dass die oben beschriebenen Probleme mit verschiedenen Methoden und mit unterschiedlichem Effizienzgrad gelöst werden können. Je mehr Daten Sie jedoch erhalten, desto verschärft werden sie.

Wenn Sie alle oben genannten Punkte haben (unter Berücksichtigung des Vorhergehenden). Artikel), sowie eine ständige Zunahme der Anzahl empfangener Metriken, der Wunsch, alle Metriken in ein Speicherintervall von 30 Sekunden zu übertragen. (bei Bedarf bis zu 10 Sekunden) haben wir uns entschieden, Graphite+ClickHouse als vielversprechende Alternative zu Whisper auszuprobieren.

Graphit+ClickHouse. Erwartungen

Ich habe mehrere Treffen der Jungs von Yandex besucht und gelesen ein paar Artikel über HabréNachdem wir die Dokumentation durchgesehen und vernünftige Komponenten für die Anbindung von ClickHouse unter Graphite gefunden hatten, beschlossen wir zu handeln!

Möchte folgendes erhalten:

  • Reduzieren Sie die Auslastung des Festplattensubsystems von 30 % auf 5 %.
  • Reduzieren Sie den belegten Speicherplatz von 1 TB auf 100 GB;
  • in der Lage sein, 100 Millionen Messwerte pro Minute an den Server zu empfangen;
  • Datenreplikation und Fehlertoleranz sofort einsatzbereit;
  • Setzen Sie sich nicht ein Jahr lang mit diesem Projekt auseinander und nehmen Sie den Übergang für einen vernünftigen Zeitraum vor.
  • Wechsel ohne Ausfallzeit.

Ziemlich ehrgeizig, oder?

Graphit+ClickHouse. Komponenten

Ich habe mich dafür entschieden, Daten über das Graphite-Protokoll zu empfangen und sie dann an ClickHouse zu schreiben Carbon-Clickhouse (Golang).

Als Datenbank zur Speicherung von Zeitreihen wurde das letzte ClickHouse-Release der stabilen Version 1.1.54253 gewählt. Bei der Arbeit damit gab es Probleme: In den Protokollen strömte ein Berg von Fehlern und es war nicht ganz klar, was man damit machen sollte. Im Gespräch mit Roman Lomonossow (Autor von Carbon-Clickhouse, Graphite-Clickhouse und vielem mehr) Die ältere Version wurde ausgewählt Version 1.1.54236. Fehler verschwanden – alles begann mit einem Knall zu funktionieren.

Zum Lesen von Daten aus ClickHouse wurde ausgewählt Graphit-Clickhouse (Golang). Als API für Graphite − Carbonapi (Golang). Um die Replikation zwischen Tabellen zu organisieren, wurde ClickHouse verwendet zookeeper. Für Routing-Metriken haben wir unsere Geliebte verlassen Carbon-C-Relais (C) (siehe vorherigen Artikel).

Graphit+ClickHouse. Tabellenstruktur

„Graphit“ ist eine Datenbank, die wir zur Überwachung von Tabellen erstellt haben.

„graphite.metrics“ ist eine Tabelle mit der ReplicatedReplacingMergeTree-Engine (replicated MergeTree ersetzen). In dieser Tabelle werden die Namen der Metriken und die Pfade zu ihnen gespeichert.

CREATE TABLE graphite.metrics ( Date Date, Level UInt32, Path String, Deleted UInt8, Version UInt32 ) ENGINE = ReplicatedReplacingMergeTree('/clickhouse/tables/replicator/graphite.metrics', ‘r1’, Date, (Level, Path), 8192, Version);

„graphite.data“ ist eine Tabelle mit der ReplicatedGraphiteMergeTree-Engine (replicated GraphiteMergeTree). In dieser Tabelle werden Metrikwerte gespeichert.

CREATE TABLE graphite.data ( Path String, Value Float64, Time UInt32, Date Date, Timestamp UInt32 ) ENGINE = ReplicatedGraphiteMergeTree('/clickhouse/tables/replicator/graphite.data', 'r1', Date, (Path, Time), 8192, 'graphite_rollup')

„graphite.date_metrics“ ist eine bedingt gefüllte Tabelle mit der ReplicatedReplacingMergeTree-Engine. Diese Tabelle enthält die Namen aller Metriken, die im Laufe des Tages aufgetreten sind. Die Gründe für die Erstellung werden im Abschnitt beschrieben „Probleme“ am Ende dieses Artikels.

CREATE MATERIALIZED VIEW graphite.date_metrics ( Path String,  Level UInt32,  Date Date) ENGINE = ReplicatedReplacingMergeTree('/clickhouse/tables/replicator/graphite.date_metrics', 'r1', Date, (Level, Path, Date), 8192) AS SELECT toUInt32(length(splitByChar('.', Path))) AS Level, Date, Path FROM graphite.data

„graphite.data_stat“ ist eine bedingte Tabelle mit der ReplicatedAggregatingMergeTree-Engine (replicated AggregatingMergeTree). In dieser Tabelle wird die Anzahl der eingehenden Metriken aufgezeichnet, aufgeschlüsselt nach 4 Verschachtelungsebenen.

CREATE MATERIALIZED VIEW graphite.data_stat ( Date Date,  Prefix String,  Timestamp UInt32,  Count AggregateFunction(count)) ENGINE = ReplicatedAggregatingMergeTree('/clickhouse/tables/replicator/graphite.data_stat', 'r1', Date, (Timestamp, Prefix), 8192) AS SELECT toStartOfMonth(now()) AS Date, replaceRegexpOne(Path, '^([^.]+.[^.]+.[^.]+).*$', '1') AS Prefix, toUInt32(toStartOfMinute(toDateTime(Timestamp))) AS Timestamp, countState() AS Count FROM graphite.data  GROUP BY Timestamp, Prefix

Graphit+ClickHouse. Schema der Interaktion von Komponenten

Metrikspeicher: Wie wir von Graphite+Whisper zu Graphite+ClickHouse gewechselt sind

Graphit+ClickHouse. Datenmigration

Wie wir uns aus den Erwartungen an dieses Projekt erinnern, sollte der Übergang zu ClickHouse ohne Ausfallzeiten erfolgen bzw. wir mussten irgendwie unser gesamtes Überwachungssystem so transparent wie möglich für unsere Benutzer auf den neuen Speicher umstellen.
Wir haben es so gemacht.

  • Carbon-c-relay wurde eine Regel hinzugefügt, um einen zusätzlichen Messwertstrom an das Carbon-Clickhouse eines der an der Replikation von ClickHouse-Tabellen beteiligten Server zu senden.

  • Wir haben ein kleines Python-Skript geschrieben, das mithilfe der Whisper-Dump-Bibliothek alle .wsp-Dateien aus unserem Speicher liest und diese Daten in 24 Threads an das oben beschriebene Carbon-Clickhouse sendet. Die Anzahl der akzeptierten metrischen Werte in Carbon-Clickhouse erreichte 125 Millionen / Minute, und ClickHouse geriet nicht einmal ins Schwitzen.

  • Wir haben in Grafana eine separate DataSource erstellt, um die in vorhandenen Dashboards verwendeten Funktionen zu debuggen. Es wurde eine Liste der von uns verwendeten Funktionen angezeigt, die jedoch nicht in Carbonapi implementiert waren. Wir haben diese Funktionen fertiggestellt und PRs an die Autoren von Carbonapi gesendet (besonderer Dank geht an sie).

  • Um die Leselast in den Balancer-Einstellungen zu ändern, haben wir die Endpunkte von graphite-api (API-Schnittstelle für Graphite+Whisper) auf carbonapi geändert.

Graphit+ClickHouse. Ergebnisse

  • reduzierte die Auslastung des Festplattensubsystems von 30 % auf 1 %;

    Metrikspeicher: Wie wir von Graphite+Whisper zu Graphite+ClickHouse gewechselt sind

  • Reduzierung des belegten Speicherplatzes von 1 TB auf 300 GB;
  • Wir sind in der Lage, 125 Millionen Messwerte pro Minute und Server zu empfangen (Spitzenwerte zum Zeitpunkt der Migration);
  • alle Metriken in ein XNUMX-Sekunden-Speicherintervall übertragen;
  • Replikation empfangener Daten und Fehlertoleranz;
  • ohne Ausfallzeit geschaltet;
  • Es hat für alles ca. 7 Wochen gedauert.

Graphit+ClickHouse. Probleme

In unserem Fall gab es einige Fallstricke. Hier ist, was uns nach der Umstellung begegnet ist.

  1. ClickHouse liest Konfigurationen nicht immer im laufenden Betrieb neu, manchmal muss es neu geladen werden. Im Fall der Beschreibung des Zookeeper-Clusters in der ClickHouse-Konfiguration wurde diese beispielsweise erst angewendet, als der Clickhouse-Server neu gestartet wurde.
  2. Es gab keine großen ClickHouse-Anfragen, daher sieht die ClickHouse-Verbindungszeichenfolge in unserem Graphite-Clickhouse so aus:
    url = "http://localhost:8123/?max_query_size=268435456&max_ast_elements=1000000"
  3. ClickHouse veröffentlicht häufig neue Versionen stabiler Versionen. Diese können Überraschungen enthalten: Seien Sie vorsichtig.
  4. Dynamisch erstellte Container in Kubernetes senden eine große Anzahl von Metriken mit kurzer und zufälliger Lebensdauer. Nach solchen Maßstäben gibt es nicht viele Punkte und es gibt keine Probleme mit dem Ort. Beim Erstellen von Abfragen ruft ClickHouse jedoch eine große Anzahl derselben Metriken aus der Tabelle „Metriken“ ab. In 90 % der Fälle liegen für sie außerhalb des Zeitfensters (24 Stunden) keine Daten vor. Die Zeit, die für die Suche nach diesen Daten in der Tabelle „Daten“ aufgewendet wird, wird jedoch verschwendet und beruht letztendlich auf einer Zeitüberschreitung. Um dieses Problem zu lösen, haben wir begonnen, eine separate Ansicht mit Informationen zu den im Laufe des Tages aufgetretenen Kennzahlen zu verwalten. Wenn wir also Berichte (Diagramme) für dynamisch erstellte Container erstellen, fragen wir nur die Metriken ab, die innerhalb des angegebenen Fensters gefunden wurden, und nicht für die gesamte Zeit, was die Erstellung von Berichten darüber erheblich beschleunigt. Dafür wurde die obige Lösung gesammelt Graphit-Clickhouse (Gabel), einschließlich der Implementierung der Arbeit mit der Tabelle date_metrics.

Graphit+ClickHouse. Stichworte

Seit Version 1.1.0 ist Graphite offiziell Support-Tags. Und wir denken aktiv darüber nach, was und wie wir diese Initiative im Graphite+Clickhouse-Stack unterstützen können.

Graphit+ClickHouse. Anomaliedetektor

Basierend auf der oben beschriebenen Infrastruktur haben wir einen Prototyp eines Anomaliedetektors implementiert, und er funktioniert! Aber über ihn - im nächsten Artikel.

Abonnieren, Pfeil nach oben drücken und glücklich sein!

Source: habr.com

Kommentar hinzufügen