Exklusive Sperren für Elemente (pessimistische Sperre)
NCache Bietet einen pessimistischen Sperrmechanismus, der ausschließlich die zwischengespeicherten Daten sperrt. Dieser Mechanismus sperrt das Element mithilfe des Sperrhandles, wodurch alle anderen Benutzer daran gehindert werden, Schreibvorgänge für dieses Cache-Element auszuführen. A LockHandle
ist jedem gesperrten Element im Cache zugeordnet, das von der Sperr-API zurückgegeben wird.
Note
Diese Funktion ist auch in verfügbar NCache Professional.
Ein gesperrtes Element kann nur abgerufen/aktualisiert oder entsperrt werden, wenn sein Sperrhandle auf API-Ebene bereitgestellt wird. Sie sollten dies jedoch mit Vorsicht tun, um Probleme mit der Datenintegrität zu vermeiden. Pessimistic Locking ist ein sehr guter Ansatz, wenn das zu erreichende Ziel Datenkonsistenz ist.
Sobald eine Sperre mit erworben wird LockHandle
gibt es zwei Mechanismen für die Freigabe. Beide Mechanismen werden im Folgenden erläutert.
Zeitbasierte Freigabe von Sperren: Sie können beim Sperren eines zwischengespeicherten Elements auch ein Sperrzeitlimit festlegen. Das Sperr-Timeout ist das Zeitintervall, nach dem die Sperre automatisch aufgehoben wird, wenn während des Timeout-Intervalls kein expliziter Aufruf zum Aufheben der Sperre erfolgt. Dadurch wird verhindert, dass Ihre Daten für unbegrenzte Zeit gesperrt werden.
Zwangsentriegelung von Sperren: In verteilten Umgebungen können Situationen auftreten, in denen eine Anwendung, die die Sperre für ein Cache-Element erworben hat, abrupt beendet wird oder eine Anwendung ihre Verarbeitung für gesperrte Daten abschließt. In einer solchen Situation möchten Sie alle von einer solchen Anwendung erworbenen Sperren aufheben. NCache stellt eine Entsperr-API bereit, die die Cache-Elementsperre zwangsweise aufhebt.
Note
Es wird empfohlen, den zeitbasierten Sperrmechanismus zu verwenden, damit der Gegenstand entsperrt wird, nachdem die Bedingung erfüllt ist, sodass die Ressourcen für die minimale Zeit erhalten bleiben.
Wann sollte pessimistisches Sperren verwendet werden?
Nehmen Sie das im vorherigen Kapitel besprochene Beispiel. Wenn für einen Aktualisierungsvorgang von zwei verschiedenen Benutzern gleichzeitig auf dasselbe Bankkonto zugegriffen wird, kann es zu einem Konflikt kommen, der zu Dateninkonsistenzen führt.
Durch die pessimistische Sperre kann in diesem Szenario jeweils ein Benutzer auf das Konto zugreifen. Bei erfolgreicher Bedienung entsperrt der Benutzer den Artikel und die Kontrolle wird freigegeben, was bedeutet, dass der zweite Benutzer nun auf das Konto zugreifen und entsprechende Änderungen vornehmen kann.
Bei diesem Ansatz bleiben die Daten konsistent und es treten keine Konflikte auf.
A LockHandle
ist mit einem Element verknüpft, um sicherzustellen, dass auf das jeweilige Element im gesamten Cache nicht zugegriffen werden kann.
NCache stellt eine Methode bereit, die ausschließlich Locking aufruft, sowie zahlreiche Überladungen, die den Locking-Mechanismus manipulieren.
Voraussetzungen:
- Lernen Sie die Standardvoraussetzungen kennen, die für die Arbeit mit allen erforderlich sind NCache Weitere Informationen zu clientseitigen Funktionen finden Sie auf der angegebenen Seite Clientseitige API-Voraussetzungen.
- Einzelheiten zur API finden Sie unter: ICache, Enthält, Zu Zählen, Insert, Zahnscheiben, LockHandle, Entfernen, Zeitspanne, öffne es.
Sperren Sie ein Element explizit
Sie können ein Element explizit sperren, bevor Sie einen Vorgang ausführen. Diese Methode erfordert a TimeSpan
um ein Element für eine bestimmte Zeit zu sperren. Wenn Sie jedoch nicht möchten, dass die erworbene Sperre abläuft, geben Sie dies an TimeSpan.Zero
. Angabe Nr TimeSpan
sperrt den Gegenstand für eine unbegrenzte Zeit.
Das Lock
Die in diesem Beispiel verwendete Methode verknüpft a LockHandle
mit einem Schlüssel. Bitte stellen Sie sicher, dass die Single LockHandle
ist einem einzigen Schlüssel zugeordnet. Lösen Sie die Verriegelung, bevor Sie den Griff erneut verwenden. andernfalls könnte es zu inkonsistentem Verhalten kommen.
Wenn ein Element bereits gesperrt ist, wird der falsche Wert zurückgegeben, Sie erhalten jedoch den aktualisierten Wert LockHandle
.
Warnung
Sperren Sie einen Artikel für das Minimum TimeSpan
um einen Stillstand oder Hungerzustand zu vermeiden.
Das folgende Beispiel erstellt a LockHandle
und sperrt dann einen Gegenstand mit dem Schlüssel Product:1001
für eine Zeitspanne von 10 Sekunden, was bedeutet, dass der Artikel nach 10 Sekunden automatisch entsperrt wird.
// Preconditions: Cache is already connected
// Item is already added in the cache
// Specify the key of the item
string key = $"Product:1001";
//Create a new LockHandle
LockHandle lockHandle = null;
// Specify time span of 10 seconds for which the item remains locked
TimeSpan lockSpan = TimeSpan.FromSeconds(10);
// Lock the item for a time span of 10 seconds
bool lockAcquired = cache.Lock(key, lockSpan, out lockHandle);
// Verify if the item is locked successfully
if (lockAcquired == true)
{
// Item has been successfully locked
}
else
{
// Key does not exist
// Item is already locked with a different LockHandle
}
Note
Um sicherzustellen, dass der Vorgang ausfallsicher ist, wird empfohlen, alle potenziellen Ausnahmen in Ihrer Anwendung zu behandeln, wie in erläutert Umgang mit Fehlern.
Sperren Sie ein Element während des Get-Vorgangs
Ein Gegenstand kann während seines Abrufs aus dem Cache gesperrt werden. Dies bedeutet, dass das Element für andere nicht zugänglich ist, es sei denn, Sie geben es frei. Im Falle einer Nichtübereinstimmung der Schlüssel wird ein Nullwert zurückgegeben.
Wenn ein Element nicht gesperrt ist und die
acquirelock
auf true gesetzt ist, erhalten Sie das Item zusammen mit dem LockHandle.Wenn ein Artikel gesperrt ist und
acquirelock
auf false gesetzt ist und wenn Sie einen falschen oder neuen leeren LockHandle übergeben, dann anull
Der Wert wird zurückgegeben, aber Sie erhalten den LockHandle, der zuvor zum Sperren des Elements verwendet wurde.Wenn ein Artikel gesperrt ist und
acquirelock
auf false gesetzt ist und korrekter LockHandle übergeben wird, der zuvor zum Sperren des Items verwendet wurde, dann erhalten Sie den Wert.
Warnung
Sperren Sie ein Element für die minimale Zeitspanne, um Deadlocks oder Thread-Aushunger zu vermeiden.
In diesem Beispiel ein Schlüssel und LockHandle
wird angegeben, um das zwischengespeicherte Objekt abzurufen und zu sperren. Sie müssen true angeben, wenn Sie die Sperre erwerben möchten. Hier wird der Artikel mit einem Ablauf von 10 Sekunden gesperrt, was bedeutet, dass der Artikel nach 10 Sekunden automatisch entsperrt wird.
// Specify the key of the item
string key = $"Product:1001";
// Set acquireLock flag as true
bool acquireLock = true;
// Specify time span of 10 seconds for which the item remains locked
TimeSpan lockSpan = TimeSpan.FromSeconds(10);
//Create a new LockHandle
LockHandle lockHandle = null;
// Lock the item for a time span of 10 seconds
var result = cache.Get<Product>(key, acquireLock, lockSpan, ref lockHandle);
// Verify if the item is locked successfully
if (result != null)
{
// Item has been successfully locked
}
else
{
// Key does not exist
// Item is already locked with a different LockHandle
}
Sperre mit Aktualisierungsvorgang aufheben
Während Sie ein Element aktualisieren, können Sie die Sperre aufheben, damit andere die zwischengespeicherten Daten verwenden können. Um das gesperrte Element erfolgreich freizugeben, müssen Sie Folgendes angeben LockHandle
ursprünglich zum Sperren des Gegenstands verwendet.
Das
LockHandle
sollte derselbe sein, der ursprünglich zum Sperren des Elements verwendet wurde. Andernfalls erhalten Sie eine Ausnahmemeldung mit der Meldung „Element ist gesperrt“.If
releaseLock
auf false gesetzt ist, müssen Sie immer noch das Richtige übergebenLockhandle
um den Artikel zu aktualisieren.Wenn ein Artikel nicht gesperrt ist, wird der
LockHandle
machenreleaseLock
sind nutzlos und werden ignoriert.
Das folgende Beispiel sperrt ein Element im Cache und ruft das Element dann mithilfe von ab LockHandle
. Das Element wird dann aktualisiert und dann mithilfe von erneut in den Cache eingefügt Insert API.
// Specify the key of the item
string key = $"Product:1001";
// Set acquireLock flag as true
bool acquireLock = true;
// Specify time span of 10 seconds for which the item remains locked
TimeSpan lockSpan = new TimeSpan(0, 0, 10);
// Initialize the lockHandle
LockHandle lockHandle = null;
CacheItem item = cache.GetCacheItem(key, acquireLock, lockSpan, ref lockHandle);
var product = new Product();
product = item.GetValue<Product>();
// Update the unitsinstock for the product
product.UnitsInStock = 200;
bool releaseLock = true;
// Item is already locked with a LockHandle
// Update the item and release the lock as well since releaseLock is set true
// Make sure that the LockHandle matches with the already added LockHandle
cache.Insert(key, item, null, lockHandle, releaseLock);
Sperre explizit aufheben
Um die Sperre für ein zuvor gesperrtes zwischengespeichertes Element explizit aufzuheben; Sie müssen das angeben LockHandle
ursprünglich zum Sperren des Gegenstands verwendet.
Besitzt das LockHandle
nicht gespeichert wird, können Sie auch eine andere Überladung von verwenden Unlock
Dafür braucht man nur den Schlüssel, um den Gegenstand zu entsperren.
Note
Wenn eine ungültige LockHandle
übergeben wird, wird keine Ausnahme ausgelöst, das Element bleibt jedoch gesperrt.
Das folgende Beispiel ruft ein bereits gesperrtes Element mithilfe von ab LockHandle
und entsperrt es dann mit dem Unlock
API mit der Lockhandle
vorher gespeichert.
// Specify the key of the item
string key = $"Product:1001";
// Set acquireLock flag as true
bool acquireLock = true;
// Specify time span of 10 seconds for which the item remains locked
TimeSpan lockSpan = TimeSpan.FromSeconds(10);
//Create a new LockHandle
LockHandle lockHandle = null;
Product result = cache.Get<Product>(key, acquireLock, lockSpan, ref lockHandle);
// Make sure that the item is already locked and the saved LockHandle is used
// Unlock locked item using saved LockHandle
cache.Unlock(key, lockHandle);
Warnung
NCache ignoriert die Sperren, wenn andere Überladungen auftreten Get
, Insert
und Remove
Es werden Methoden aufgerufen, die weder nehmen noch verwenden LockHandle
.
Element mit LockHandle entfernen
Die Remove-Methode ist eine grundlegende Methode, die den Schlüssel aus dem Cache entfernt und das entfernte Objekt an den Client zurückgibt. Wenn dem Cache ein benutzerdefiniertes Objekt hinzugefügt wird, gibt die Methode „Objekt“ zurück.
LockHandle
Es sollte dasselbe sein, das ursprünglich zum Sperren des Elements verwendet wurde. Andernfalls erhalten Sie die Ausnahmemeldung „Element ist gesperrt“.Wenn ein Artikel nicht gesperrt ist, dann
LockHandle
ist nutzlos und seine Gültigkeit wird nicht überprüft.
Das folgende Beispiel ruft ein Element ab, das zuvor mithilfe von gesperrt wurde LockHandle
und entfernt es dann durch das Gespeicherte LockHandle
aus dem Cache mit dem Entfernen API.
Tipp
Sie können die Entfernung überwachen/verifizieren:
- "Cache Count"-Zähler ein NCache Überwachen or PerfMon-Zähler.
- Die richtigen
cache.Contains
nach Ablauf des Ablaufintervalls. - Die richtigen
cache.Count
vor und nach Angabe des Ablaufs.
// Specify the key of the item
string key = $"Product:1001";
// Initialize the lockHandle
LockHandle lockHandle = null;
// Set acquireLock flag as true
bool acquireLock = true;
// Specify time span of 10 seconds for which the item remains locked
TimeSpan lockSpan = TimeSpan.FromSeconds(10);
// Get the item using the lockHandle
Product result = cache.Get<Product>(key, acquireLock, lockSpan, ref lockHandle);
// Removing locked item using saved lockHandle.
cache.Remove(key, lockHandle);
// Check if item is successfully removed
if (result != null)
{
if (result is Product)
{
Product product = (Product)result;
}
}
Besondere Überlegungen bei der Verwendung der API-Sperre
NCache stellt eine Reihe von APIs mit und ohne bereit LockHandle
um das Cache-Element abzurufen/aktualisieren. APIs ohne a LockHandle
Elementsperre ignorieren. Daher sollten Sie alle Sperr-APIs zur Datenmanipulation verwenden. Wenn beispielsweise ein Element gesperrt ist und Sie einen Aktualisierungs-API-Aufruf durchführen, der das nicht annimmt LockHandle
als Eingabeparameter, dann wird das Element unabhängig von seinem Sperrstatus im Cache aktualisiert.
Wichtig
Wenn Sie eine Sperrfunktion verwenden, sollten Sie nur API-Aufrufe verwenden, die dauern LockHandle
als Parameter. Eine API, die keine Sperrhandles akzeptiert, kann verwendet werden, sollte jedoch mit größter Sorgfalt erfolgen, damit die Datenintegrität nicht beeinträchtigt wird.
Note
Im Falle einer Räumung/Ablauf, NCache ignoriert Sperren, was bedeutet, dass ein gesperrtes Element aufgrund von Ablauf oder Räumung entfernt werden kann.
Topologieweises Verhalten
- Gespiegelte und replizierte Topologie
Im Spiegel Topologie: Für alle Sperrvorgänge wird eine Sperre auf dem aktiven Knoten erworben, und das Gleiche LockHandle
wird dann auf den Passivknoten repliziert, sodass das Element gesperrt bleibt, wenn Passiv zu Aktiv wird. In ähnlicher Weise wird der Entsperraufruf auch auf den Passivknoten repliziert, um das Element vom Passivknoten zu entsperren.
Im Repliziert Topologie: Der Client ist mit einem Knoten verbunden und für alle Sperrvorgänge gilt der LockHandle
wird generiert, der den Client-Sperrvorgang empfängt, und dann das Gleiche LockHandle
werden aus Gründen der Datenkonsistenz auf alle anderen Knoten repliziert. In ähnlicher Weise wird der Entsperrvorgang auch auf alle anderen Knoten repliziert.
- Partitionierte und Partitionsreplikat-Topologie
Im Partitioniert Topologie, LockHandle
wird generiert und existiert auf demselben Knoten, der das Element enthält, und während der Statusübertragung LockHandle
Informationen werden auch zusammen mit dem Element übertragen, falls das Element zu einem anderen Knoten verschoben wird.
In Partitionsreplikat Topologie, LockHandle
wird auf dem aktiven Knoten generiert, der das Element enthält, und dasselbe LockHandle
wird dann aus Gründen der Datenkonsistenz und während der Zustandsübertragung auf sein Replikat repliziert. LockHandle
Informationen werden auch zusammen mit dem Element übertragen, falls das Element auf einen anderen Knoten verschoben wird.
- Client-Cache
Im Client-Cache, alle sperrenbasierten Vorgänge werden direkt im Cluster-Cache ausgeführt, was bedeutet, dass LockHandle
wird generiert und im Cluster-Cache gespeichert. Im Client-Cache werden keine sperrbezogenen Informationen verwaltet.
Weitere Informationen
NCache stellt eine Beispielanwendung für die Artikelsperre bereit GitHub.
Siehe auch
.NETZ: Alachisoft.NCache.Runtime.Caching Namespace.
Java: com.alachisoft.ncache.runtime.caching Namespace.
Node.js: Cache-Speicher Klasse.
Python: ncache.runtime.caching Klasse.