Wie werden Deadlocks in einem RDBMS erkannt und gemeldet?

8

Diese Frage wurde mir während eines Interviews gestellt, bekam aber den Job nicht. Die vollständige Frage lautete wie folgt:

Wie werden Deadlocks in einem RDBMS erkannt und gemeldet? Was sind der Transaktionsinhaber und der Anwendungsentwickler dafür verantwortlich, sowohl in Erkennungs- als auch in Präventionsszenarien sicherzustellen?

Shadowcaz
quelle

Antworten:

13

In SQL Server gibt es einen separaten Thread, der regelmäßig (Standard 5 Sekunden, niedrigeres Intervall, wenn gerade ein Deadlock erkannt wurde) eine Liste der Wartezeiten auf Zyklen überprüft. Das heißt, es identifiziert die Ressource, auf die ein Thread wartet, dann findet es den Eigentümer dieser Ressource und findet rekursiv die Ressource, auf die der Thread wiederum wartet, wodurch Threads identifiziert werden, die auf die Ressourcen des jeweils anderen warten.

Wenn ein Deadlock gefunden wird, wird ein Opfer ausgewählt, das mit diesem Algorithmus getötet werden soll:

  1. Identifizieren Sie Threads, die nicht nicht getötet werden können (z. B. ein Thread, der eine Transaktion zurücksetzt, kann nicht getötet werden).
  2. Suchen Sie den Thread mit der niedrigsten Deadlock-Priorität.
  3. Wählen Sie diejenige, die am billigsten zurückgesetzt werden kann, dh diejenige, die bisher am wenigsten Arbeit geleistet hat.

Weitere Informationen zur Deadlock-Erkennung von SQL Servern finden Sie hier: http://msdn.microsoft.com/en-us/library/ms178104.aspx



Der Transaktionsinhaber / Anwendungsentwickler ist dafür verantwortlich, das Risiko von Deadlocks zu minimieren und zu tun dass sie sollten:

  1. Stellen Sie sicher, dass die Transaktionen so kurz wie möglich sind. Zeigen Sie beispielsweise nach dem Starten einer Transaktion kein Anmeldeformular an und warten Sie auf Benutzereingaben. Sammeln Sie stattdessen alle erforderlichen Informationen und führen Sie die Transaktion aus.
  2. Verwenden Sie die niedrigstmögliche Isolationsstufe, z. B. nicht serialisierbar, wenn Sie dem Benutzer nur vorübergehend einige Werte anzeigen möchten. Bitte beachten Sie, dass das Einstellen der richtigen Isolationsstufe eine Wissenschaft für sich ist und in dieser Antwort nicht berücksichtigt wird.
  3. Wenn Sie Opfer eines Deadlocks sind, dh Fehler # 1205 erhalten, führen Sie Ihre Transaktion für Ihren Benutzer transparent erneut aus. Da die andere konkurrierende Transaktion nun hoffentlich die Ressourcen erworben hat, auf die sie gewartet und die sie abgeschlossen hat, ist es unwahrscheinlich, dass Sie erneut auf denselben Deadlock stoßen.
Andreas Ågren
quelle
4. Erwerben Sie Ressourcen und führen Sie Aktualisierungs- / Lösch- / Einfügemuster in derselben Reihenfolge in der gesamten Anwendung durch.
ErikE
3
@ErikE Es ist häufig nicht möglich / machbar, "Muster in der gesamten Anwendung konsistent in derselben Reihenfolge zu aktualisieren / löschen / einfügen", obwohl dieser fragwürdige Rat im Web sehr beliebt ist. Details hier: sqlblog.com/blogs/alexander_kuznetsov/archive/2010/01/15/…
AK
1
Gute Argumente. Aber ich denke immer noch, dass sich die Mühe lohnt, solange man sich keine Illusion macht, dass es immer möglich sein oder das Problem immer beheben wird. Die Eltern / Kind-Sache ist interessant. Wie wäre es, wenn Sie zuerst Kaskaden löschen oder eine Aktualisierungssperre für die Elternzeilen erwerben? Und wenn Sie ohne MERGE fusionieren, warum nicht konsistent sein? Ich lösche-> update-> persönlich einfügen.
ErikE
1
@AlexKuznetsov: Es ist keine Solver-Kugel, sollte aber nicht abgewiesen werden. Ich habe Deadlocks auf diese Weise reduziert (nicht beseitigt): durch statische Analyse von häufig ausgeführtem Code, der jeden Tag oder 7 Deadlocks verursachte. Ich würde vorschlagen, dass "vorzeitige Optimierung" usw.
angewendet wird
Ich bin mit Empfehlung Nummer 3 nicht einverstanden. Wenn wir nach Deadlocks erneut versuchen, überschreiben wir sehr wahrscheinlich die Änderungen anderer Prozesse. Wir müssen uns bewusst sein, dass höchstwahrscheinlich jemand anderes die Daten geändert hat, die wir ändern wollten. Insbesondere wenn alle Leser unter Snapshot-Isolation ausgeführt werden, können die Leser nicht an Deadlocks beteiligt sein. Dies bedeutet, dass alle an einem Deadlock beteiligten Parteien Schreiber sind, die dieselben Daten geändert oder versucht haben, sie zu ändern. Wenn wir nur die Ausnahme abfangen und es automatisch erneut versuchen, können wir die Änderungen eines anderen überschreiben. Dies wird als verlorene Updates bezeichnet und ist normalerweise falsch.
AK