Detaillierte Erläuterung der Idee der verteilten Sperre in MySQL mit Hilfe von DB

Detaillierte Erläuterung der Idee der verteilten Sperre in MySQL mit Hilfe von DB

Vorwort

Unabhängig davon, ob es sich um eine eigenständige oder eine verteilte Sperre handelt, besteht das Prinzip darin, das Verhalten des aktuellen Vorgangs anhand gemeinsam genutzter Daten zu beurteilen. Bei einer einzelnen Maschine wird der RAM-Speicher gemeinsam genutzt, bei einem Cluster kann dies mithilfe von Komponenten von Drittanbietern wie Redis, ZK, DB usw. erreicht werden. Redis und ZK bieten hervorragende Unterstützung für verteilte Sperren und sind grundsätzlich sofort einsatzbereit. Diese Komponenten selbst müssen jedoch hochverfügbar sein, und das System muss sich auch stark auf diese Komponenten verlassen, was erhebliche zusätzliche Kosten verursacht. DB ist standardmäßig eine hochverfügbare Komponente für das System. Die Verwendung von DB zur Implementierung verteilter Sperren ist auch eine gute Lösung für einige Geschäfte mit geringer Frequenz, z. B. die Steuerung des Starts geplanter Aufgaben auf mehreren Computern und die Verarbeitung von Genehmigungsrückrufen. Dieser Artikel enthält einige Szenarien und Lösungen zur Implementierung verteilter Sperren mit DB und soll Sie inspirieren.

Tischdesign

Zunächst einmal sollte klar sein, dass die DB immer noch das anfälligste Glied im System ist. Daher müssen Druckprobleme beim Entwurf berücksichtigt werden. Das heißt, Logik, die von der Anwendung implementiert werden kann, sollte nicht auf der DB implementiert werden. Mit anderen Worten, die von der DB bereitgestellten Sperrfunktionen sollten so wenig wie möglich verwendet werden. Wenn es sich um ein Geschäft mit hoher Parallelität handelt, sollten DB-Sperren vermieden werden. Es ist effektiver, stattdessen Cache-Sperren wie Redis zu verwenden. Wie in Listing 1 gezeigt, ist die einzige Einschränkung in der Tabelle der Primärschlüssel, der aus lock_name, timestamp und version besteht. Diese drei Schlüssel werden im Folgenden verwendet, um Geschäftsszenarien wie pessimistisches und optimistisches Sperren zu implementieren.

Listing 1: Verteilte Sperrtabellenstruktur

CREATE TABLE `Sperre` (
`lock_name` varchar(32) NOT NULL DEFAULT '' COMMENT 'Sperrname',
`Ressource` bigint(20) NOT NULL COMMENT 'Primärschlüssel des Unternehmens',
`version` int(5) NICHT NULL KOMMENTAR 'Version',
`gmt_create` datetime NICHT NULL KOMMENTAR 'Generierungszeit',
PRIMÄRSCHLÜSSEL (`Sperrname`,`Ressource`,`Version`)
)ENGINE=InnoDB STANDARD-CHARSET=utf8mb4;

Pessimistische Sperrimplementierung

Im pessimistischen Sperrgeschäft gibt es zwei gängige Vorgänge:


Für A:

In Szenario A befinden sich, nachdem eine Maschine die Sperre erhalten hat, andere Maschinen in einem Warteschlangenzustand. Sie können erst fortfahren, nachdem die Sperre aufgehoben wurde. Diese Lösung auf Anwendungsebene ist ziemlich problematisch. Daher wird im Allgemeinen die von der Datenbank bereitgestellte Zeilensperrfunktion verwendet, d. h., zum Aktualisieren wird xxx aus xxx ausgewählt. Szenario A ist im Allgemeinen eng mit dem Geschäft verbunden, beispielsweise einer Bestandserhöhung oder -verringerung, und das Geschäftsobjekt kann als Zeilensperre verwendet werden. Es ist zu beachten, dass der Sperrdruck dieser Lösung im Wesentlichen auf der Datenbank liegt. Wenn zu viele Threads blockiert sind und der Vorgang zeitaufwändig ist, kommt es schließlich zu einer großen Anzahl von Sperrzeitüberschreitungen.

Für B:

Für Szenario B (tryLock) nehmen wir als Beispiel ein bestimmtes Unternehmen. Im Cluster hat jede Maschine eine geplante Aufgabe, aber das Unternehmen erfordert, dass normalerweise nur eine Maschine gleichzeitig geplant werden kann.
Die Lösung besteht darin, die eindeutige Primärschlüsseleinschränkung zu verwenden, um einen Datensatz für TaskA einzufügen. Die Standardversion ist 1. Wenn das Einfügen erfolgreich ist, wird die Sperre erhalten und der Geschäftsbetrieb kann fortgesetzt werden. Diese Lösung führt zu einem Deadlock, wenn die Maschine hängt. Daher ist auch eine geplante Aufgabe erforderlich, um abgelaufene Sperren regelmäßig zu bereinigen. Die Bereinigungsdimension kann je nach Sperrenname unterschiedliche Zeitbereinigungsstrategien festlegen.

Die Bereinigungsstrategie für geplante Aufgaben bringt zusätzliche Komplexität mit sich. Angenommen, Maschine A erhält die Sperre, aber aufgrund von CPU-Ressourcenbeschränkungen verlangsamt sich die Verarbeitung. Zu diesem Zeitpunkt wird die Sperre durch die geplante Aufgabe freigegeben, sodass Maschine B ebenfalls die Sperre erhält. In diesem Fall halten zwei Maschinen gleichzeitig die Sperre. Die Lösung besteht darin, die Zeitüberschreitungszeit deutlich länger als die Geschäftsverarbeitungszeit einzustellen oder einen Versionsmechanismus hinzuzufügen, um auf optimistische Sperrung umzustellen.

In Sperrsatz einfügen lock_name='TaskA' , resource='Geschäft gesperrt', version=1, gmt_create=now()
Erfolg: Holen Sie sich die Sperre. Fehlgeschlagen: Brechen Sie den Vorgang ab und geben Sie die Sperre frei.

Implementierung optimistischer Sperren

Nehmen wir für das Szenario mit optimistischer Sperre ein bestimmtes Unternehmen als Beispiel. Im Hintergrundsystem werden häufig große JSON-Erweiterungsfelder zum Speichern von Geschäftsattributen verwendet. Bei teilweisen Aktualisierungen müssen Sie diese zuerst abfragen, die Daten zusammenführen und in die Datenbank schreiben. Wenn dieser Vorgang parallel abläuft, kann es leicht zu Datenverlust kommen. Daher sind Sperren erforderlich, um die Datenkonsistenz sicherzustellen. Die entsprechenden Vorgänge sind unten dargestellt. Bei optimistischen Sperren gibt es keine Deadlocks, sodass das Feld „Geschäfts-ID“ direkt hier gespeichert wird, um sicherzustellen, dass jede Geschäfts-ID einen entsprechenden Datensatz hat und nicht vom entsprechenden Timer gelöscht werden muss.

Wählen Sie * aus der Sperre, wobei lock_name = 'Firmenname', resource = 'Firmen-ID';
Existiert nicht: In Sperrsatz einfügen: lock_name='Firmenname', resource='Firmen-ID', version=1;
Version abrufen: Version
Geschäftsvorgänge: Daten abrufen, Daten zusammenführen, Daten zurück in die Datenbank schreiben: Sperrsatz aktualisieren Version=Version+1, wobei Sperrname=„Firmenname“ und Ressource=„Firmen-ID“ und Version= #{Version};
Rückschreiben erfolgreich: Vorgang erfolgreich. Rückschreiben fehlgeschlagen: Machen Sie die Transaktion rückgängig und beginnen Sie von vorne.

Wenn ein Schreibvorgang mit optimistischer Sperre fehlschlägt, wird die gesamte Transaktion zurückgesetzt. Daher sind optimistische Sperren nicht für Szenarien geeignet, in denen Schreibkonflikte häufig auftreten. Eine große Anzahl von Transaktions-Rollbacks übt enormen Druck auf die Datenbank aus und wirkt sich letztendlich auf das jeweilige Geschäftssystem aus.

Zusammenfassen

Das Prinzip der verteilten Sperren ist eigentlich leicht zu verstehen, die Schwierigkeit liegt jedoch darin, die am besten geeignete Lösung für bestimmte Geschäftsszenarien auszuwählen. Unabhängig davon, welche Sperrlösung verwendet wird, hängt sie eng mit dem Geschäft zusammen. Kurz gesagt, es gibt keine perfekte verteilte Sperrlösung, sondern nur die Sperrlösung, die am besten zum aktuellen Geschäft passt.

Das ist alles für diesen Artikel. Ich hoffe, dass der Inhalt dieses Artikels für Ihr Studium oder Ihre Arbeit von gewissem Referenzwert ist. Vielen Dank für Ihre Unterstützung von 123WORDPRESS.COM.

Das könnte Sie auch interessieren:
  • Java verwendet das Implementierungsprinzip der verteilten Sperre von Redisson
  • Java-Programmierung Redisson zur Implementierung eines Codebeispiels für verteilte Sperren
  • Zusammenfassung der korrekten Implementierungsmethode für verteilte Redis-Sperren
  • So implementieren Sie die verteilte Sperre von Redis (Redis-Interviewfrage)
  • Codebeispiel für verteilte Sperren in Springboot Redis
  • SpringBoot verwendet Redisson, um verteilte Sperren zu implementieren (Second-Kill-System)
  • Beispiel dafür, wie SpringBoot Redisson integriert, um verteilte Sperren zu implementieren
  • Detaillierte Erläuterung der korrekten Implementierung der verteilten Sperre von Java Redis
  • Detaillierte Erläuterung des von Java Redisson implementierten Prinzips der verteilten Sperre

<<:  Verwendung von Docker-Image-Speicher-Overlays

>>:  Grundlegende Anwendungsbeispiele für Listener in Vue

Artikel empfehlen

Detaillierte Erklärung zur Verwendung des Canvas-Operation-Plugins fabric.js

Fabric.js ist ein sehr nützliches Plug-In für Can...

js implementiert das klassische Minesweeper-Spiel

In diesem Artikelbeispiel wird der spezifische Co...

Detaillierte Einführung in den MySQL Innodb Index-Mechanismus

1. Was ist ein Index? Ein Index ist eine Datenstr...

So zeichnen Sie die Zeitleiste mit Vue+Canvas

In diesem Artikelbeispiel wird der spezifische Co...

Natives js zum Erzielen eines Akkordeoneffekts

Auch bei der tatsächlichen Entwicklung von Websei...

Die große Rolle von HTML-Meta

Es gibt zwei Metaattribute: Name und http-equiv. D...

Lösung für mehrere Docker-Container, die nicht die gleiche Portnummer haben

Hintergrund In Docker werden vier Container mit d...

Beispielcode des Spread-Operators und seiner Anwendung in JavaScript

Der Spread-Operator ermöglicht die Erweiterung ei...

Reagiert auf verschiedene Arten, Parameter zu übergeben

Inhaltsverzeichnis Übergeben von Parametern zwisc...