TIP: Blocker erkennen mit SQL Guard 2000

zurück

Autor : Sancho Fock
In einer Client Server Datenbank greifen viele Benutzer auf die gleichen Ressourcen zu, so daß es zwangsläufig zu Blocksituationen kommt. Das stellt auch kein Problem dar, wenn die einzelnen Sperren (bzw. deren Transaktionen) nur kurzlebig sind. Kurzlebig nach dieser Definition sind Transaktionen, die nicht länger als drei Sekunden dauern. Das Auftreten dieser kurzzeitigen Blocksituationen kann vernachlässigt werden, es sei denn, diese treten so häufig auf, daß es zu Schneeballeffekten kommt.
Anders stellt sich die Situation dar, wenn es im System zu mittellanglebigen Transaktionen (durchschnittliche Lebensdauer von ca. 4 Sekunden bis 10 Minuten) oder gar langlebigen Transaktionen (durchschnittliche Lebensdauer liegt über 10 Minuten) kommt. Diese Arten von Blocksituationen deuten auf einen Fehler in der Applikation hin. (Mehr Informationen zu Lösungsstrategien bei den verschiedenen Arten von Blocksituationen finden Sie in dem Artikel Anti Blocker Strategien desselben Autors).
Die langlebigen Transaktionen können gut mit manuellen Mitteln - wie sie beispielsweise in der Microsoft Knowledge Base beschrieben sind - erkannt werden (Art. Q271509 und Q224453 ). Anders hingegen die mittellanglebigen Transaktionen: Sie dauern lange genug, um den Betrieb einer Anwendung zum Erlahmen zu bringen, sind aber meist zu kurz, um sie manuell analysieren zu können. Hier setzt nun der SQL Guard 2000 ein: Sobald er eine Blocksituation identifiziert hat, protokolliert er die Informationen. Darüber hinaus sorgt er dafür, daß trotz langlebiger Blocksituation der Betrieb der restlichen User aufrechterhalten werden kann, indem er bei zu lange andauernder Blocksituation (einstellbares Intervall) den blockierenden Prozeß terminiert.
Die Arbeitsweise des SQL Guards 2000 wird im Folgenden an einem Beispiel vorgestellt:
Nachdem die Datenbankverbindung des SQL Guards in der Datei SQLGuard.Udl eingerichtet wurde, kann der SQL Guard 2000 gestartet werden. Eingestellt werden können dann die Intervalle, in denen die Prüfungen vorgenommen werden sollen.
Für dieses Beispiel werden folgende Intervalle konfiguriert:
Checkintervall = 5 Sekunden
Killintervall = 10 Prüfungen
Aufgrund dieser Einstellungen kann ein Prozeß maximal 54 Sekunden andere Prozesse blockieren, bevor er terminiert wird.
Sind die Intervalle eingestellt, kann die Prüfung auf Blocks aktiviert und die Überwachung gestartet werden. Der SQL Guard quittiert die erfolgreiche Verbindung mit dem Datenbankserver und ist bereit.

Seitenanfang



Um die genaue Arbeitsweise des SQL Guards 2000 zu demonstrieren, wird eine Blocksituation erzeugt. Dazu wird ein Fenster im Query Analyser (QA) geöffnet und folgende Transaktion ausgeführt:

      begin transaction
          select * from customers
          update customers 
              set City = 'GB-London' 
                  where City = 'London'
          while (1=1) begin
              select @@version 
          end
      rollback transaction
Dadurch haben wir einen typischen Blocker Prozess. Zur eigentlichen Blocksituation kommt es aber erst, wenn ein User die gelockte Ressource abfragt. Deshalb wird jetzt ein zweites QA Fenster geöffnet und folgende Abfrage ausgeführt:

      select * from customers
Damit liegt eine Blocksituation vor: Der Prozeß im ersten QA Fenster blockiert den Prozess im zweiten QA Fenster.
Der SQL Guard merkt dies sofort:

Seitenanfang



Welche Informationen gibt nun der SQL Guard 2000?
Dafür muss man sich das Log etwas genauer ansehen: Zuerst folgt die Meldung der festgestellten Blocksituation. Daraufhin folgen alle wichtigen Informationen zu der Blocksituation:

06.02.2003 23:12:03 *** SQL Guard LOCKCHECK: Blocksituation festgestellt :
Process : 7 Prozess ID des Blockers
Geblockter Process : 9 Prozess ID des geblockten Prozesses
Station : THS-MOB Name der Workstation des Blocker Prozesses
User : Username des Blockers (ist nur von Bedeutung, wenn der Prozess sich mit integrierter Sicherheit angemeldet hat)
Domain : Domain des Blockers (ist nur von Bedeutung, wenn der Prozess sich mit integrierter Sicherheit angemeldet hat)
Login : sa SQL Server Loginname des Blockers
Datenbank : Northwind Datenbankname, auf der die Blocksituation stattgefunden hat.
Programm : MS SQL Query Analyze Name der Applikation, die den Block verursacht hat
CPU : 0 CPU Status des Blocker Prozesses
IO : 54 IO des Blockers

Bei einer zweischichtigen Anwendung reichen diese Informationen in der Regel aus, um denjenigen Programmteil ausfindig zu machen, der den Fehler enthält. Als zusätzliche Sicherheit zur Fehleridentifikation erhält derjenige User eine Nachricht, der den blockierenden Prozeß ausgeführt hatte (und dessen Datenbankprozess terminiert wurde).
Diese Informationen reichen allerdings nicht aus, wenn es sich um eine mehrschichtige Anwendung handelt, bei der von der Workstation des SQL-Server Clientprozesses nicht auf den Endanwender geschlossen werden kann. Für diesen Fall werden mehr Informationen benötigt.
(Für spätere Versionen ist geplant, Interfaces für J2EE Container, MTS und CORBA Objekte bereitzustellen, um die nötigen Informationen aus dem Applikationsserver zu erhalten.)
Als nächstes folgt eine Liste der Ressourcen, die der Blockerprozess gesperrt hat und es folgen Angaben über den Inputbuffer des Blockers:

Geblockte Resouce(en)
ObjectID --> ObjectName
213575799 --> Customers                     
BLOCKING Statement : Typ: Language Event - Parameter: 0 - 
SQL: begin transaction
  select * from customers
  update customers 
    set City = 'GB-London' 
      where City = 'London'
while (1=1) begin
  select @@version 
end
rollback transaction
BLOCKED Statement : Typ: Language Event - Parameter: 0 - 
SQL: select * from customers
Seitenanfang

Aus dem Inputbuffer wird ersichtlich, welche Abfrage der blockierende Prozeß vor seiner Terminierung an den SQL Server gestellt hat. Aufgrund dieser Angabe kann diese nun bekannte Abfrage in der Anwendung gesucht und damit die Transaktion ausfindig gemacht werden, welche das Problem verursacht hat.
Die Suche nach der Transaktion wird jedoch dadurch erschwert, daß das Statement im Inputbuffer des Blockers nicht unbedingt das Statement sein muß, welches den Block verursacht hat (Es ist aber auf jeden Fall ein Statement in derselben Transaktion).
Aus diesem Grunde gibt der SQL Guard 2000 zusätzlich eine Liste der geblockten Ressourcen aus, damit mit Hilfe dieser Informationen besser erkannt werden kann, um welche Transaktion es sich handelt.
Beispiel: Eine Transaktion, die unter anderem die Tabelle "orders" gesperrt hat, hat wahrscheinlich mit dem Bestellwesen der Anwendung zu tun.
Sollten diese Informationen aber immer noch nicht ausreichen, die gesuchte Transaktion ausfindig zu machen, kann ein Blick auf den Outputbuffer des Blockers weiterhelfen. Dieser enthält einen Auszug aus den Daten, die der SQL-Server zuletzt an den blockierenden Prozeß gesendet hat.

Outputbuffer : 
v.M.i.c.r.o..o.f.t. .S.Q.L..S.e.r.v.e.r. ..7...0.0. .-. ....0.0...6.2.3..(.I.n.t.e.l. ..8.6.). 
.....N..v. .2.7. .1.9..8. .2.2.:.2.0..0.7. .....C.o..y.r.i.g.h.t. ..c.). .1.9.8.8..1.9.9.8. .M
.i..r.o.s.o.f.t. ..o.r.p.o.r.a.t.. o.n.....D.e.v..l.o.p.e.r. .E..i.t.i.o.n. .o.. .W.i.n.d.o.w.
. .N.T. .5...1..(.B.u.i.l.d. ..6.0.0.:. .S.e..v.i.c.e. .P.a..k. .1.)..........................
.v...v.M.i..r.o.s.o .f.t. ..Q.L. .S.e.r.v..r. . .7...0.0..-. .7...0.0....2.3. .(.I.n.t.
Die abschließe Protokollierung des SQL Guards 2000 beinhaltet die Information darüber, wie lange der Blocker blockiert hat und ob er terminiert wurde:

*** SQL Guard LOCKCHECK: Der blockierende Process 7 besteht weiterhin! Alter min: 5 sekunden
…
*** SQL Guard LOCKCHECK: Der blockierende Process 7 besteht weiterhin! Alter min: 45 sekunden
*** SQL Guard LOCKCHECK: Der blockierende Process 7 wurde terminiert
Bei einer Blocksituation stellt der SQL Guard 2000 die Informationen zur Verfügung, die benötigt werden, den Fehler ausfindig zu machen. Die Protokollierung bietet den Vorteil, daß zu jeder Zeit nachvollzogen werden kann, was auf der Datenbank passiert ist, ohne zum Zeitpunkt des Blockes unmittelbar anwesend sein zu müssen. Das Beispiel hat gezeigt, daß der SQL Guard 2000 auch bei gravierenden Fehlern in der Lage ist, den Betrieb sicher zu stellen. Das gibt den Entwicklern zum einen die Möglichkeit, Probleme zu erkennen, und zum anderen verschafft es ihnen (in der Regel) ausreichend Zeit, um das Problem sorgfältig zu analysieren.

Es ist nicht immer einfach, den Grund für eine Blocksituation zu finden. Um sinnvolle Strategien entwickeln zu können, ist es unerläßlich, sich zu verdeutlichen, welche Arten von Fehlern Blocksituationen verursachen. Der SQL Guard 2000 bietet ihnen eine Möglichkeit an, der Sache schnell auf die Spur zu kommen.

Sie können sich selber von den Vorteilen des SQL Guards überzeugen;
eine kostenlose Demoversion des SQL Guards 2000 kann hier heruntergeladen werden.

zurück