In unseren vorherigen Blogs haben wir MHA als Failover-Tool besprochen, das in MySQL-Master-Slave-Setups verwendet wird. Letzten Monat haben wir auch darüber gebloggt, wie man mit MHA umgeht, wenn es abstürzt. Heute werden wir die wichtigsten Probleme sehen, auf die DBAs normalerweise mit MHA stoßen, und wie Sie sie beheben können.
Eine kurze Einführung in MHA (Master High Availability)
MHA steht für (Master High Availability) und ist auch heute noch relevant und weit verbreitet, insbesondere in Master-Slave-Setups, die auf Nicht-GTID-Replikation basieren. MHA eignet sich gut als Failover oder Master-Switch, bringt jedoch einige Fallstricke und Einschränkungen mit sich. Sobald MHA ein Master-Failover und eine Slave-Hochstufung durchführt, kann es seinen Datenbank-Failover-Vorgang automatisch innerhalb von ca. 30 Sekunden abschließen, was in einer Produktionsumgebung akzeptabel sein kann. MHA kann die Konsistenz der Daten sicherstellen. All dies ohne Leistungseinbußen, und es sind keine zusätzlichen Anpassungen oder Änderungen an Ihren bestehenden Bereitstellungen oder Setups erforderlich. Abgesehen davon baut MHA auf Perl auf und ist eine Open-Source-HA-Lösung – daher ist es relativ einfach, Hilfsprogramme zu erstellen oder das Tool gemäß Ihrem gewünschten Setup zu erweitern. Weitere Informationen finden Sie in dieser Präsentation.
MHA-Software besteht aus zwei Komponenten, Sie müssen eines der folgenden Pakete entsprechend seiner Topologierolle installieren:
MHA-Managerknoten =MHA-Manager (Manager)/MHA-Knoten (Datenknoten)
Master/Slave-Knoten =MHA-Knoten (Datenknoten)
MHA Manager ist die Software, die das Failover verwaltet (automatisch oder manuell), Entscheidungen darüber trifft, wann und wo ein Failover erfolgen soll, und die Slave-Wiederherstellung während der Heraufstufung des Kandidaten-Masters zum Anwenden von Differential-Relay-Protokollen verwaltet. Wenn die Master-Datenbank stirbt, koordiniert der MHA-Manager den MHA-Knotenagenten, da er differenzielle Relay-Protokolle auf die Slaves anwendet, die nicht über die neuesten Binlog-Ereignisse vom Master verfügen. Die MHA-Node-Software ist ein lokaler Agent, der Ihre MySQL-Instanz überwacht und es dem MHA-Manager ermöglicht, Relay-Protokolle von den Slaves zu kopieren. Ein typisches Szenario ist, dass der Kandidaten-Master für Failover derzeit verzögert und MHA erkennt, dass er nicht über die neuesten Relay-Protokolle verfügt. Daher wartet er auf sein Mandat vom MHA-Manager, während er nach dem neuesten Slave sucht, der die Binlog-Ereignisse enthält, und fehlende Ereignisse vom Slave mithilfe von scp kopiert und auf sich selbst anwendet.
Beachten Sie jedoch, dass MHA derzeit nicht aktiv gepflegt wird, aber die aktuelle Version selbst stabil ist und möglicherweise „gut genug“ für die Produktion ist. Sie können Ihre Stimme immer noch über Github wiedergeben, um einige Probleme zu beheben oder Patches für die Software bereitzustellen.
Häufigste Probleme
Sehen wir uns nun die häufigsten Probleme an, auf die ein DBA bei der Verwendung von MHA stoßen wird.
Slave verzögert, nicht interaktives/automatisches Failover fehlgeschlagen!
Dies ist ein typisches Problem, das dazu führt, dass das automatische Failover abgebrochen wird oder fehlschlägt. Das mag einfach klingen, weist aber nicht nur auf ein bestimmtes Problem hin. Slave Lag kann verschiedene Gründe haben:
- Festplattenprobleme auf dem Kandidaten-Master, die dazu führen, dass es sich um eine Festplatten-E/A handelt, die an die Verarbeitung von Lese- und Schreibvorgängen gebunden ist. Es kann auch zu Datenbeschädigung führen, wenn es nicht gemildert wird.
- Fehlerhafte Abfragen werden repliziert, insbesondere Tabellen, die keine Primärschlüssel oder geclusterten Indizes haben.
- hohe Serverlast.
- Kalter Server und Server ist noch nicht aufgewärmt
- Nicht genügend Serverressourcen. Möglicherweise hat Ihr Slave zu wenig Arbeitsspeicher oder Serverressourcen, während er hochintensive Schreib- oder Lesevorgänge repliziert.
Diese können im Voraus gemildert werden, wenn Sie Ihre Datenbank ordnungsgemäß überwachen. Ein Beispiel in Bezug auf Slave-Verzögerungen in MHA ist wenig Arbeitsspeicher beim Sichern einer großen binären Protokolldatei. Als Beispiel unten wurde ein Master als tot markiert und muss ein nicht interaktives/automatisches Failover durchführen. Da der Kandidaten-Master jedoch verzögert war und die Protokolle anwenden muss, die noch nicht von den Replikations-Threads ausgeführt wurden, findet MHA den aktuellsten oder neuesten Slave, da er versucht, einen Slave gegen den ältesten wiederherzustellen Einsen. Wie Sie unten sehen können, ging der Speicher daher während der Durchführung einer Slave-Wiederherstellung zu niedrig aus:
[email protected]:~$ masterha_manager --conf=/etc/app1.cnf --remove_dead_master_conf --ignore_last_failover
Mon May 6 08:43:46 2019 - [warning] Global configuration file /etc/masterha_default.cnf not found. Skipping.
Mon May 6 08:43:46 2019 - [info] Reading application default configuration from /etc/app1.cnf..
Mon May 6 08:43:46 2019 - [info] Reading server configuration from /etc/app1.cnf..
…
Mon May 6 08:43:57 2019 - [info] Checking master reachability via MySQL(double check)...
Mon May 6 08:43:57 2019 - [info] ok.
Mon May 6 08:43:57 2019 - [info] Alive Servers:
Mon May 6 08:43:57 2019 - [info] 192.168.10.50(192.168.10.50:3306)
Mon May 6 08:43:57 2019 - [info] 192.168.10.70(192.168.10.70:3306)
Mon May 6 08:43:57 2019 - [info] Alive Slaves:
Mon May 6 08:43:57 2019 - [info] 192.168.10.50(192.168.10.50:3306) Version=5.7.23-23-log (oldest major version between slaves) log-bin:enabled
Mon May 6 08:43:57 2019 - [info] Replicating from 192.168.10.60(192.168.10.60:3306)
Mon May 6 08:43:57 2019 - [info] Primary candidate for the new Master (candidate_master is set)
Mon May 6 08:43:57 2019 - [info] 192.168.10.70(192.168.10.70:3306) Version=5.7.23-23-log (oldest major version between slaves) log-bin:enabled
Mon May 6 08:43:57 2019 - [info] Replicating from 192.168.10.60(192.168.10.60:3306)
Mon May 6 08:43:57 2019 - [info] Not candidate for the new Master (no_master is set)
Mon May 6 08:43:57 2019 - [info] Starting Non-GTID based failover.
….
Mon May 6 08:43:59 2019 - [info] * Phase 3.4: New Master Diff Log Generation Phase..
Mon May 6 08:43:59 2019 - [info]
Mon May 6 08:43:59 2019 - [info] Server 192.168.10.50 received relay logs up to: binlog.000004:106167341
Mon May 6 08:43:59 2019 - [info] Need to get diffs from the latest slave(192.168.10.70) up to: binlog.000005:240412 (using the latest slave's relay logs)
Mon May 6 08:43:59 2019 - [info] Connecting to the latest slave host 192.168.10.70, generating diff relay log files..
Mon May 6 08:43:59 2019 - [info] Executing command: apply_diff_relay_logs --command=generate_and_send --scp_user=vagrant --scp_host=192.168.10.50 --latest_mlf=binlog.000005 --latest_rmlp=240412 --target_mlf=binlog.000004 --target_rmlp=106167341 --server_id=3 --diff_file_readtolatest=/tmp/relay_from_read_to_latest_192.168.10.50_3306_20190506084355.binlog --workdir=/tmp --timestamp=20190506084355 --handle_raw_binlog=1 --disable_log_bin=0 --manager_version=0.58 --relay_dir=/var/lib/mysql --current_relay_log=relay-bin.000007
Mon May 6 08:44:00 2019 - [info]
Relay log found at /var/lib/mysql, up to relay-bin.000007
Fast relay log position search failed. Reading relay logs to find..
Reading relay-bin.000007
Binlog Checksum enabled
Master Version is 5.7.23-23-log
Binlog Checksum enabled
…
…...
Target relay log file/position found. start_file:relay-bin.000004, start_pos:106167468.
Concat binary/relay logs from relay-bin.000004 pos 106167468 to relay-bin.000007 EOF into /tmp/relay_from_read_to_latest_192.168.10.50_3306_20190506084355.binlog ..
Binlog Checksum enabled
Binlog Checksum enabled
Dumping binlog format description event, from position 0 to 361.. ok.
Dumping effective binlog data from /var/lib/mysql/relay-bin.000004 position 106167468 to tail(1074342689)..Out of memory!
Mon May 6 08:44:00 2019 - [error][/usr/local/share/perl/5.26.1/MHA/MasterFailover.pm, ln1090] Generating diff files failed with return code 1:0.
Mon May 6 08:44:00 2019 - [error][/usr/local/share/perl/5.26.1/MHA/MasterFailover.pm, ln1584] Recovering master server failed.
Mon May 6 08:44:00 2019 - [error][/usr/local/share/perl/5.26.1/MHA/ManagerUtil.pm, ln178] Got ERROR: at /usr/local/bin/masterha_manager line 65.
Mon May 6 08:44:00 2019 - [info]
----- Failover Report -----
app1: MySQL Master failover 192.168.10.60(192.168.10.60:3306)
Master 192.168.10.60(192.168.10.60:3306) is down!
Check MHA Manager logs at testnode20 for details.
Started automated(non-interactive) failover.
Invalidated master IP address on 192.168.10.60(192.168.10.60:3306)
The latest slave 192.168.10.70(192.168.10.70:3306) has all relay logs for recovery.
Selected 192.168.10.50(192.168.10.50:3306) as a new master.
Recovering master server failed.
Got Error so couldn't continue failover from here.
Daher ist das Failover fehlgeschlagen. Das obige Beispiel zeigt, dass der Knoten 192.168.10.70 die aktuellsten Relay-Protokolle enthält. In diesem Beispielszenario wird der Knoten 192.168.10.70 jedoch als no_master festgelegt, da er wenig Arbeitsspeicher hat. Der Versuch, den Slave 192.168.10.50 wiederherzustellen, scheitert!
Korrekturen/Lösung:
Dieses Szenario veranschaulicht etwas sehr Wichtiges. Eine erweiterte Überwachungsumgebung muss eingerichtet werden! Beispielsweise können Sie ein Hintergrund- oder Daemon-Skript ausführen, das den Replikationszustand überwacht. Sie können als Eintrag über einen Cron-Job hinzufügen. Fügen Sie beispielsweise einen Eintrag mit dem integrierten Skript masterha_check_repl hinzu :
/usr/local/bin/masterha_check_repl --conf=/etc/app1.cnf
oder erstellen Sie ein Hintergrundskript, das dieses Skript aufruft und in einem Intervall ausführt. Sie können die Option report_script verwenden, um eine Warnmeldung einzurichten, falls sie nicht Ihren Anforderungen entspricht, z. B. wenn der Slave während einer hohen Spitzenlast etwa 100 Sekunden verzögert. Sie können auch Überwachungsplattformen wie ClusterControl verwenden, um Ihnen Benachrichtigungen basierend auf den Metriken zu senden, die Sie überwachen möchten.
Beachten Sie außerdem, dass im Beispielszenario das Failover aufgrund eines Fehlers wegen unzureichendem Arbeitsspeicher fehlgeschlagen ist. Sie könnten in Betracht ziehen, sicherzustellen, dass alle Ihre Knoten über genügend Speicher und die richtige Größe der Binärlogs verfügen, da sie das Binlog für eine Slave-Wiederherstellungsphase ausgeben müssten.
Inkonsistenter Slave, Anwenden von Diffs fehlgeschlagen!
In Bezug auf Slave-Lag, da MHA versuchen wird, Relay-Logs mit einem Kandidaten-Master zu synchronisieren, stellen Sie sicher, dass Ihre Daten synchron sind. Sagen Sie für ein Beispiel unten:
...
Concat succeeded.
Generating diff relay log succeeded. Saved at /tmp/relay_from_read_to_latest_192.168.10.50_3306_20190506054328.binlog .
scp testnode7:/tmp/relay_from_read_to_latest_192.168.10.50_3306_20190506054328.binlog to [email protected](22) succeeded.
Mon May 6 05:43:53 2019 - [info] Generating diff files succeeded.
Mon May 6 05:43:53 2019 - [info]
Mon May 6 05:43:53 2019 - [info] * Phase 3.5: Master Log Apply Phase..
Mon May 6 05:43:53 2019 - [info]
Mon May 6 05:43:53 2019 - [info] *NOTICE: If any error happens from this phase, manual recovery is needed.
Mon May 6 05:43:53 2019 - [info] Starting recovery on 192.168.10.50(192.168.10.50:3306)..
Mon May 6 05:43:53 2019 - [info] Generating diffs succeeded.
Mon May 6 05:43:53 2019 - [info] Waiting until all relay logs are applied.
Mon May 6 05:43:53 2019 - [info] done.
Mon May 6 05:43:53 2019 - [info] Getting slave status..
Mon May 6 05:43:53 2019 - [info] This slave(192.168.10.50)'s Exec_Master_Log_Pos equals to Read_Master_Log_Pos(binlog.000010:161813650). No need to recover from Exec_Master_Log_Pos.
Mon May 6 05:43:53 2019 - [info] Connecting to the target slave host 192.168.10.50, running recover script..
Mon May 6 05:43:53 2019 - [info] Executing command: apply_diff_relay_logs --command=apply --slave_user='cmon' --slave_host=192.168.10.50 --slave_ip=192.168.10.50 --slave_port=3306 --apply_files=/tmp/relay_from_read_to_latest_192.168.10.50_3306_20190506054328.binlog --workdir=/tmp --target_version=5.7.23-23-log --timestamp=20190506054328 --handle_raw_binlog=1 --disable_log_bin=0 --manager_version=0.58 --slave_pass=xxx
Mon May 6 05:43:53 2019 - [info]
MySQL client version is 5.7.23. Using --binary-mode.
Applying differential binary/relay log files /tmp/relay_from_read_to_latest_192.168.10.50_3306_20190506054328.binlog on 192.168.10.50:3306. This may take long time...
mysqlbinlog: Error writing file 'UNOPENED' (Errcode: 32 - Broken pipe)
FATAL: applying log files failed with rc 1:0!
Error logs from testnode5:/tmp/relay_log_apply_for_192.168.10.50_3306_20190506054328_err.log (the last 200 lines)..
ICwgMmM5MmEwZjkzY2M5MTU3YzAxM2NkZTk4ZGQ1ODM0NDEgLCAyYzkyYTBmOTNjYzkxNTdjMDEz
….
…..
M2QxMzc5OWE1NTExOTggLCAyYzkyYTBmOTNjZmI1YTdhMDEzZDE2NzhiNDc3NDIzNCAsIDJjOTJh
MGY5M2NmYjVhN2EwMTNkMTY3OGI0N2Q0MjMERROR 1062 (23000) at line 72: Duplicate entry '12583545' for key 'PRIMARY'
5ICwgMmM5MmEwZjkzY2ZiNWE3YTAxM2QxNjc4YjQ4
OTQyM2QgLCAyYzkyYTBmOTNjZmI1YTdhMDEzZDE2NzhiNDkxNDI1MSAsIDJjOTJhMGY5M2NmYjVh
N2EwMTNkMTczN2MzOWM3MDEzICwgMmM5MmEwZjkzY2ZiNWE3YTAxM2QxNzM3YzNhMzcwMTUgLCAy
…
--------------
Bye
at /usr/local/bin/apply_diff_relay_logs line 554.
eval {...} called at /usr/local/bin/apply_diff_relay_logs line 514
main::main() called at /usr/local/bin/apply_diff_relay_logs line 121
Mon May 6 05:43:53 2019 - [error][/usr/local/share/perl/5.26.1/MHA/MasterFailover.pm, ln1399] Applying diffs failed with return code 22:0.
Mon May 6 05:43:53 2019 - [error][/usr/local/share/perl/5.26.1/MHA/MasterFailover.pm, ln1584] Recovering master server failed.
Mon May 6 05:43:53 2019 - [error][/usr/local/share/perl/5.26.1/MHA/ManagerUtil.pm, ln178] Got ERROR: at /usr/local/bin/masterha_manager line 65.
Mon May 6 05:43:53 2019 - [info]
Ein inkonsistenter Cluster ist wirklich schlecht, besonders wenn automatisches Failover aktiviert ist. In diesem Fall kann das Failover nicht fortgesetzt werden, da es einen doppelten Eintrag für den Primärschlüssel „12583545“ erkennt '.
Korrekturen/Lösung:
Hier können Sie mehrere Dinge tun, um einen inkonsistenten Status Ihres Clusters zu vermeiden.
- Aktivieren Sie die verlustfreie halbsynchrone Replikation. Sehen Sie sich diesen externen Blog an, in dem Sie erfahren, warum Sie die Verwendung von Semi-Sync in einem standardmäßigen MySQL-Replikations-Setup in Betracht ziehen sollten.
- Lassen Sie ständig eine Prüfsumme gegen Ihren Master-Slave-Cluster laufen. Sie können pt-table-checksum verwenden und es einmal pro Woche oder Monat ausführen, je nachdem, wie ständig Ihre Tabelle aktualisiert wird. Beachten Sie, dass pt-table-checksum den Datenverkehr Ihrer Datenbank erhöhen kann.
- Verwenden Sie die GTID-basierte Replikation. Dies wirkt sich jedoch nicht auf das Problem an sich aus. Die GTID-basierte Replikation hilft Ihnen jedoch, fehlerhafte Transaktionen zu ermitteln, insbesondere solche Transaktionen, die direkt auf dem Slave ausgeführt wurden. Ein weiterer Vorteil davon ist, dass es einfacher ist, die GTID-basierte Replikation zu verwalten, wenn Sie den Master-Host in der Replikation wechseln müssen.
Hardwarefehler auf dem Master, aber Slaves haben noch nicht aufgeholt
Einer der vielen Gründe, warum Sie in automatisches Failover investieren sollten, ist ein Hardwarefehler auf dem Master. Für einige Setups kann es idealer sein, ein automatisches Failover nur durchzuführen, wenn der Master einen Hardwarefehler feststellt. Der typische Ansatz besteht darin, durch Senden eines Alarms zu benachrichtigen – was bedeuten kann, dass die Bereitschaftsperson mitten in der Nacht geweckt wird, damit die Person entscheiden kann, was zu tun ist. Diese Art von Ansatz wird auf Github oder sogar Facebook durchgeführt. Ein Hardwarefehler, insbesondere wenn das Volume betroffen ist, auf dem sich Ihre Binlogs und Ihr Datenverzeichnis befinden, kann Ihr Failover durcheinander bringen, insbesondere wenn die Binärprotokolle auf dieser ausgefallenen Festplatte gespeichert sind. MHA versucht standardmäßig, Binärprotokolle vom abgestürzten Master zu speichern, aber dies ist nicht möglich, wenn die Festplatte ausgefallen ist. Ein mögliches Szenario ist, dass der Server nicht über SSH erreichbar ist. MHA kann keine Binärprotokolle speichern und muss ein Failover durchführen, ohne Binärprotokollereignisse anzuwenden, die nur auf dem abgestürzten Master vorhanden sind. Dadurch gehen die neuesten Daten verloren, insbesondere wenn kein Slave den Master eingeholt hat.
Korrekturen/Lösung
Als einer der Anwendungsfälle von MHA wird empfohlen, die halbsynchrone Replikation zu verwenden, da sie das Risiko eines solchen Datenverlusts erheblich reduziert. Es ist wichtig zu beachten, dass alle Schreibvorgänge, die an den Master gehen, sicherstellen müssen, dass die Slaves die neuesten Binärprotokollereignisse empfangen haben, bevor sie mit der Festplatte synchronisiert werden. MHA kann die Ereignisse auf alle anderen Slaves anwenden, damit sie miteinander konsistent sind.
Darüber hinaus ist es besser, einen Backup-Stream Ihrer Binärprotokolle für die Notfallwiederherstellung auszuführen, falls das Hauptfestplattenvolume ausgefallen ist. Wenn der Server immer noch über SSH erreichbar ist, kann es immer noch funktionieren, den Binärlog-Pfad auf den Backup-Pfad Ihres Binärlogs zu verweisen, sodass Failover und Slave-Wiederherstellung immer noch vorankommen können. So vermeiden Sie Datenverlust.
VIP-Failover (virtuelle IP) verursacht Split-Brain
MHA übernimmt standardmäßig keine VIP-Verwaltung. Es ist jedoch einfach, dies in die MHA-Konfiguration zu integrieren und Hooks entsprechend dem zuzuweisen, was MHA während des Failovers tun soll. Sie können Ihr eigenes Skript erstellen und es mit den Parametern master_ip_failover_script oder master_ip_online_change_script verknüpfen. Es gibt auch Beispielskripts, die sich im Verzeichnis
Sobald Ihr Skript mit der VIP-Verwaltung aufgerufen und ausgeführt wird, führt MHA bei einem automatischen Failover Folgendes aus:Status prüfen, altes VIP entfernen (oder stoppen) und dann neues VIP dem neuen Master zuweisen. Ein typisches Beispiel für Split Brain ist, wenn ein Master aufgrund eines Netzwerkproblems als tot identifiziert wird, Slave-Knoten jedoch immer noch in der Lage sind, eine Verbindung zum Master herzustellen. Dies ist ein Fehlalarm und führt häufig zu Dateninkonsistenzen zwischen den Datenbanken im Setup. Eingehende Client-Verbindungen, die den VIP verwenden, werden an den neuen Master gesendet. Auf der anderen Seite können lokale Verbindungen auf dem alten Master laufen, der angeblich tot ist. Die lokalen Verbindungen könnten den Unix-Socket oder localhost verwenden, um Netzwerksprünge zu verringern. Dies kann dazu führen, dass die Daten gegen den neuen Master und den Rest seiner Slaves driften, da Daten vom alten Master nicht in die Slaves repliziert werden.
Korrekturen/Lösung:
Wie bereits erwähnt, ziehen es einige vor, ein automatisches Failover zu vermeiden, es sei denn, die Überprüfungen haben ergeben, dass der Master vollständig ausgefallen ist (wie ein Hardwarefehler), d. h. selbst die Slave-Knoten können ihn nicht erreichen. Die Idee ist, dass ein falsch positives Ergebnis durch einen Netzwerkfehler zwischen dem MHA-Knotencontroller und dem Master verursacht werden könnte, sodass ein Mensch in diesem Fall möglicherweise besser geeignet ist, eine Entscheidung darüber zu treffen, ob ein Failover durchgeführt wird oder nicht.
Beim Umgang mit Fehlalarmen hat MHA einen Parameter namens secondary_check_script. Der hier platzierte Wert kann Ihr benutzerdefiniertes Skript sein oder Sie können das integrierte Skript /usr/local/bin/masterha_secondary_check verwenden die zusammen mit dem MHA Manager-Paket geliefert wird. Dies fügt zusätzliche Überprüfungen hinzu, was eigentlich der empfohlene Ansatz ist, um Fehlalarme zu vermeiden. Im Beispiel unten aus meinem eigenen Setup verwende ich das eingebaute Skript masterha_secondary_check :
secondary_check_script=/usr/local/bin/masterha_secondary_check -s 192.168.10.50 --user=root --master_host=testnode6 --master_ip=192.168.10.60 --master_port=3306
Im obigen Beispiel führt der MHA-Manager eine Schleife basierend auf der Liste der Slave-Knoten (angegeben durch das Argument -s) aus, die die Verbindung mit dem MySQL-Master-Host (192.168.10.60) prüft. Beachten Sie, dass diese Slave-Knoten in dem Beispiel einige externe Remote-Knoten sein können, die eine Verbindung zu den Datenbankknoten innerhalb des Clusters herstellen können. Dies ist ein empfohlener Ansatz, insbesondere für Setups, bei denen MHA Manager in einem anderen Rechenzentrum oder anderen Netzwerk als die Datenbankknoten ausgeführt wird. Die folgende Sequenz unten veranschaulicht, wie es mit den Prüfungen fortfährt:
- Vom MHA-Host -> TCP-Verbindung zum 1. Slave-Knoten prüfen (IP:192.168.10.50). Nennen wir dies Verbindung A. Dann prüft der Slave-Knoten die TCP-Verbindung zum Master-Knoten (192.168.10.60). Nennen wir diese Verbindung B.
Wenn "Verbindung A" erfolgreich war, aber "Verbindung B" in beiden Routen nicht erfolgreich war, masterha_secondary_check Das Skript wird mit dem Rückgabecode 0 beendet und der MHA-Manager entscheidet, dass der MySQL-Master wirklich tot ist, und beginnt mit dem Failover. Wenn "Verbindung A" nicht erfolgreich war, masterha_secondary_check wird mit Rückkehrcode 2 beendet und MHA Manager geht davon aus, dass ein Netzwerkproblem vorliegt, und startet kein Failover. Wenn "Verbindung B" erfolgreich war, masterha_secondary_check wird mit Rückgabecode 3 beendet und MHA Manager erkennt, dass der MySQL-Masterserver tatsächlich aktiv ist, und startet kein Failover.
Ein Beispiel dafür, wie es während des Failovers reagiert, basierend auf dem Protokoll,
Tue May 7 05:31:57 2019 - [info] OK.
Tue May 7 05:31:57 2019 - [warning] shutdown_script is not defined.
Tue May 7 05:31:57 2019 - [info] Set master ping interval 1 seconds.
Tue May 7 05:31:57 2019 - [info] Set secondary check script: /usr/local/bin/masterha_secondary_check -s 192.168.10.50 -s 192.168.10.60 -s 192.168.10.70 --user=root --master_host=192.168.10.60 --master_ip=192.168.10.60 --master_port=3306
Tue May 7 05:31:57 2019 - [info] Starting ping health check on 192.168.10.60(192.168.10.60:3306)..
Tue May 7 05:31:58 2019 - [warning] Got error on MySQL connect: 2003 (Can't connect to MySQL server on '192.168.10.60' (110))
Tue May 7 05:31:58 2019 - [warning] Connection failed 1 time(s)..
Tue May 7 05:31:58 2019 - [info] Executing SSH check script: exit 0
Tue May 7 05:31:58 2019 - [info] Executing secondary network check script: /usr/local/bin/masterha_secondary_check -s 192.168.10.50 -s 192.168.10.60 -s 192.168.10.70 --user=root --master_host=192.168.10.60 --master_ip=192.168.10.60 --master_port=3306 --user=vagrant --master_host=192.168.10.60 --master_ip=192.168.10.60 --master_port=3306 --master_user=cmon [email protected] --ping_type=SELECT
Master is reachable from 192.168.10.50!
Tue May 7 05:31:58 2019 - [warning] Master is reachable from at least one of other monitoring servers. Failover should not happen.
Tue May 7 05:31:59 2019 - [warning] Got error on MySQL connect: 2003 (Can't connect to MySQL server on '192.168.10.60' (110))
Tue May 7 05:31:59 2019 - [warning] Connection failed 2 time(s)..
Tue May 7 05:32:00 2019 - [warning] Got error on MySQL connect: 2003 (Can't connect to MySQL server on '192.168.10.60' (110))
Tue May 7 05:32:00 2019 - [warning] Connection failed 3 time(s)..
Tue May 7 05:32:01 2019 - [warning] Got error on MySQL connect: 2003 (Can't connect to MySQL server on '192.168.10.60' (110))
Tue May 7 05:32:01 2019 - [warning] Connection failed 4 time(s)..
Tue May 7 05:32:03 2019 - [warning] HealthCheck: Got timeout on checking SSH connection to 192.168.10.60! at /usr/local/share/perl/5.26.1/MHA/HealthCheck.pm line 343.
Tue May 7 05:32:03 2019 - [warning] Secondary network check script returned errors. Failover should not start so checking server status again. Check network settings for details.
Tue May 7 05:32:04 2019 - [warning] Got error on MySQL connect: 2003 (Can't connect to MySQL server on '192.168.10.60' (110))
Tue May 7 05:32:04 2019 - [warning] Connection failed 1 time(s)..
Tue May 7 05:32:04 2019 - [info] Executing secondary network check script: /usr/local/bin/masterha_secondary_check -s 192.168.10.50 -s 192.168.10.60 -s 192.168.10.70 --user=root --master_host=192.168.10.60 --master_ip=192.168.10.60 --master_port=3306 --user=vagrant --master_host=192.168.10.60 --master_ip=192.168.10.60 --master_port=3306 --master_user=cmon [email protected] --ping_type=SELECT
Tue May 7 05:32:04 2019 - [info] Executing SSH check script: exit 0
Eine weitere Sache, die hinzugefügt werden muss, ist die Zuweisung eines Werts zum Parameter shutdown_script. Dieses Skript ist besonders nützlich, wenn Sie ein richtiges STONITH- oder Node-Fencing implementieren müssen, damit es nicht von den Toten aufersteht. Dadurch können Dateninkonsistenzen vermieden werden.
Stellen Sie schließlich sicher, dass sich der MHA-Manager zusammen mit den Cluster-Knoten im selben lokalen Netzwerk befindet, da dies die Möglichkeit von Netzwerkausfällen verringert, insbesondere die Verbindung von MHA-Manager zu den Datenbankknoten.
SPOF bei MHA vermeiden
MHA kann aus verschiedenen Gründen abstürzen, und leider gibt es keine integrierte Funktion, um dies zu beheben, z. B. Hochverfügbarkeit für MHA. Wie wir jedoch in unserem vorherigen Blog „Master High Availability Manager (MHA) ist abgestürzt! Was mache ich jetzt?“ besprochen haben, gibt es eine Möglichkeit, SPOF für MHA zu vermeiden.
Korrekturen/Lösung:
Sie können Pacemaker nutzen, um aktive/Standby-Knoten zu erstellen, die vom Cluster-Ressourcen-Manager (crm) verwaltet werden. Alternativ können Sie ein Skript erstellen, um den Zustand des MHA-Manager-Knotens zu überprüfen. Beispielsweise können Sie einen Standby-Knoten bereitstellen, der den MHA-Manager-Knoten aktiv überprüft, indem er per SSH das integrierte Skript masterha_check_status ausführt wie unten:
[email protected]:~$ /usr/local/bin/masterha_check_status --conf=/etc/app1.cnf
app1 is stopped(2:NOT_RUNNING).
Führen Sie dann ein Knoten-Fencing durch, wenn dieser Controller gebohrt ist. Sie können das MHA-Tool auch mit einem Hilfsskript erweitern, das über einen Cron-Job ausgeführt wird, und den Systemprozess des masterha_manager-Skripts überwachen und es neu starten, wenn der Prozess tot ist.
Datenverlust während Failover
MHA stützt sich auf die herkömmliche asynchrone Replikation. Obwohl Semi-Sync unterstützt wird, ist Semi-Sync dennoch auf asynchrone Replikation angewiesen. In dieser Art von Umgebung kann es nach einem Failover zu Datenverlusten kommen. Wenn Ihre Datenbank nicht richtig eingerichtet ist und einen altmodischen Replikationsansatz verwendet, kann dies ein Problem sein, insbesondere wenn es um Datenkonsistenz und verlorene Transaktionen geht.
Eine weitere wichtige Sache, die bei Datenverlust mit MHA zu beachten ist, ist, wenn GTID ohne aktivierte Halbsynchronisierung verwendet wird. MHA mit GTID stellt keine Verbindung über ssh zum Master her, sondern versucht zuerst, die Binärprotokolle für die Knotenwiederherstellung mit den Slaves zu synchronisieren. Dies kann möglicherweise zu mehr Datenverlust führen als im Vergleich zu MHA ohne GTID mit nicht aktiviertem Semi-Sync.
Korrekturen/Lösung
Erstellen Sie beim Durchführen eines automatischen Failovers eine Liste mit Szenarien, in denen Sie erwarten, dass Ihr MHA ein Failover durchführt. Da es sich bei MHA um die Master-Slave-Replikation handelt, raten wir Ihnen zur Vermeidung von Datenverlusten wie folgt:
- Verlustfreie Semi-Sync-Replikation aktivieren (vorhanden in Version MySQL 5.7)
- Verwenden Sie die GTID-basierte Replikation. Natürlich können Sie die traditionelle Replikation verwenden, indem Sie die x- und y-Koordinaten von binlog verwenden. Es macht die Dinge jedoch schwieriger und zeitaufwändiger, wenn Sie einen bestimmten Binärlogeintrag finden müssen, der nicht auf dem Slave angewendet wurde. Daher ist es mit GTID in MySQL einfacher, fehlerhafte Transaktionen zu erkennen.
- Aktivieren Sie für die ACID-Konformität Ihrer MySQL-Master-Slave-Replikation diese spezifischen Variablen:sync_binlog =1, innodb_flush_log_at_trx_commit =1. Dies ist teuer, da es mehr Rechenleistung erfordert, wenn MySQL die fsync()-Funktion aufruft, wenn es festgeschrieben wird, und mehr Leistung kann bei einer hohen Anzahl von Schreibvorgängen festplattengebunden sein. Die Verwendung von RAID mit Batterie-Backup-Cache spart jedoch Ihre Festplatten-I/O. Darüber hinaus hat sich MySQL selbst mit Binärlog-Gruppen-Commit verbessert, aber die Verwendung eines Backup-Cache kann einige Festplattensynchronisierungen sparen.
- Nutzen Sie parallele Replikation oder Multithread-Slave-Replikation. Dies kann Ihren Slaves helfen, leistungsfähiger zu werden, und vermeidet Slave-Lags gegenüber dem Master. Sie möchten nicht, dass Ihr automatisches Failover auftritt, wenn der Master überhaupt nicht über eine ssh- oder TCP-Verbindung erreichbar ist oder wenn ein Festplattenfehler aufgetreten ist und Ihre Slaves hinterherhinken. Das könnte zu Datenverlust führen.
- Wenn Sie ein Online- oder manuelles Failover durchführen, sollten Sie es am besten außerhalb der Spitzenzeiten durchführen, um unerwartete Pannen zu vermeiden, die zu Datenverlust führen könnten. Oder um zeitaufwändige Suchvorgänge zu vermeiden, während eine Menge Aktivitäten im Gange sind.
MHA sagt, APP wird nicht ausgeführt oder Failover funktioniert nicht. Was soll ich tun?
Das Ausführen von Prüfungen mit dem integrierten Skript masterha_check_status überprüft, ob das Skript masterha_manager ausgeführt wird. Andernfalls erhalten Sie eine Fehlermeldung wie die folgende:
[email protected]:~$ /usr/local/bin/masterha_check_status --conf=/etc/app1.cnf app1 is stopped(2:NOT_RUNNING).
Es gibt jedoch bestimmte Fälle, in denen Sie möglicherweise NOT_RUNNING erhalten, selbst wenn masterha_manager läuft. Dies kann an den Rechten des von Ihnen festgelegten ssh_user liegen, oder Sie führen masterha_manager mit einem anderen Systembenutzer aus, oder der ssh-Benutzer hat eine verweigerte Berechtigung festgestellt.
Korrekturen/Lösung:
MHA verwendet den ssh_user in der Konfiguration definiert, falls angegeben. Andernfalls wird der aktuelle Systembenutzer verwendet, den Sie zum Aufrufen der MHA-Befehle verwenden. Beim Ausführen des Skripts masterha_check_status Beispielsweise müssen Sie sicherstellen, dass masterha_manager mit demselben Benutzer ausgeführt wird, der in ssh_user angegeben ist in Ihrer Konfigurationsdatei oder der Benutzer, der mit den anderen Datenbankknoten im Cluster kommuniziert. Sie müssen sicherstellen, dass es passwortlose SSH-Schlüssel ohne Passphrase gibt, damit MHA keine Probleme beim Herstellen einer Verbindung zu den von MHA überwachten Knoten hat.
Beachten Sie, dass Sie den ssh_user benötigen um Zugriff auf Folgendes zu haben:
- Kann die Binär- und Relay-Logs der MySQL-Knoten lesen, die MHA überwacht
- Muss Zugriff auf die MHA-Überwachungsprotokolle haben. Sehen Sie sich diese Parameter in MHA an:master_binlog_dir, manager_workdir und manager_log
- Muss Zugriff auf die MHA-Konfigurationsdatei haben. Dies ist auch sehr wichtig. Während eines Failovers versucht es, sobald es das Failover beendet hat, die Konfigurationsdatei zu aktualisieren und den Eintrag des toten Masters zu entfernen. Wenn die Konfigurationsdatei den ssh_user oder dem Benutzer des Betriebssystems, den Sie gerade verwenden, wird die Konfigurationsdatei nicht aktualisiert, was zu einer Eskalation des Problems führt, wenn die Katastrophe erneut eintritt.
Candidate Master Lags, wie man ein fehlgeschlagenes Failover erzwingt und vermeidet
In Bezug auf MHAs Wiki wählt MHA standardmäßig, wenn ein Slave hinter dem Master mehr als 100 MB Relay-Logs hat (=mehr als 100 MB Relay-Logs anwenden muss), den Slave nicht als neuen Master, weil die Wiederherstellung zu lange dauert .
Korrekturen/Lösung
In MHA kann dies überschrieben werden, indem der Parameter check_repl_delay=0 gesetzt wird. Während eines Failovers ignoriert MHA die Replikationsverzögerung bei der Auswahl eines neuen Masters und führt fehlende Transaktionen aus. Diese Option ist nützlich, wenn Sie Candidate_master=1 auf einem bestimmten Host setzen und sicherstellen möchten, dass der Host ein neuer Master sein kann.
Sie können auch pt-heartbeat integrieren, um eine Genauigkeit der Slave-Verzögerung zu erreichen (siehe diesen Beitrag und diesen). Dies kann jedoch auch durch parallele Replikation oder Multithread-Replikations-Slaves gemildert werden, die seit MySQL 5.6 vorhanden sind, oder mit MariaDB 10 - die behauptet, einen Schub mit 10-facher Verbesserung der parallelen Replikation und Multithread-Slaves zu haben. Dies kann Ihren Sklaven helfen, sich schneller zu replizieren.
MHA-Passwörter werden offengelegt
Das Sichern oder Verschlüsseln der Passwörter wird nicht von MHA gehandhabt. Die Parameter password oder repl_password werden über die Konfigurationsdatei verfügbar gemacht. So your system administrator or security architect must evaluate the grants or privileges of this file as you don’t want to expose valuable database/SSH credentials.
Fixes/Resolution:
MHA has an optional parameter init_conf_load_script. This parameter can be used to have a custom script load your MHA config that will interface to e.g. a database, and retrieve the user/password credentials of your replication setup.
Of course, you can also limit the file attribute of the configuration and the user you are using, and limit the access to the specific Ops/DBA's/Engineers that will handle MHA.
MHA is Not My Choice, What Are the Alternatives for replication failover?
MHA is not a one-size-fits-all solution, it has its limitations and may not fit your desired setup. However, here's a list of variants that you can try.
- PRM
- Maxscale with Mariadb Monitor or MariaDB Replication Manager (MRM)
- Orchestrator
- ClusterControl