Click here to view and discuss this page in DocCommentXchange. In the future, you will be sent there automatically.

SQL Anywhere 12.0.1 (Deutsch) » SQL Anywhere Server - SQL-Benutzerhandbuch » Transaktionen und Isolationsstufen » Praktische Einführung in Isolationsstufen » Praktische Einführung: Einführung in Phantomzeilen

 

Lektion 2: Vermeiden von Phantomzeilen

 Snapshot-Isolation zur Vermeidung von Phantomzeilen verwenden

Sie können die Snapshot-Isolationsstufe verwenden, um die Konsistenz auf der gleichen Stufe aufrechtzuerhalten wie auf Isolationsstufe 3, ohne dass es zu Blockierungen kommt. Die Anweisung des "Sales Managers" wird nicht blockiert und der "Accountant" sieht keine Phantomzeile.

Falls Sie dies noch nicht getan haben, führen Sie die Schritte 1 bis 4 der praktische Einführung in Phantomzeilen durch, die beschreiben, wie Sie zwei Instanzen von Interactive SQL starten. Siehe Praktische Einführung: Einführung in Phantomzeilen.

  1. Aktivieren Sie die Snapshot-Isolation für den "Accountant", indem Sie die folgenden Anweisungen ausführen.

    SET OPTION PUBLIC. allow_snapshot_isolation = 'On';
    SET TEMPORARY OPTION isolation_level = 'snapshot';
  2. Geben Sie im Fenster des "Accountants" die folgende Anweisung ein, um alle Abteilungen aufzulisten:

    SELECT * FROM Departments
    ORDER BY DepartmentID;
    DepartmentID DepartmentName DepartmentHeadID
    100 R & D 501
    200 Sales 902
    300 Finance 1293
    400 Marketing 1576
    500 Shipping 703
  3. Der "Sales Manager" beschließt, eine neue Abteilung aufzubauen, die sich auf den ausländischen Markt konzentriert. Philip Chin, der die Mitarbeiternummer (EmployeeID) 129 hat, leitet die neue Abteilung.

    INSERT INTO Departments
       ( DepartmentID, DepartmentName, DepartmentHeadID )
       VALUES( 600, 'Foreign Sales', 129 );
    COMMIT;

    Die letzte Anweisung erstellt den Eintrag für die neue Abteilung ("Foreign Sales"). Sie erscheint als neue Zeile am Ende der Tabelle im Fenster des "Sales Managers".

    SELECT * FROM Departments
    ORDER BY DepartmentID;
    DepartmentID DepartmentName DepartmentHeadID
    100 R & D 501
    200 Sales 902
    300 Finance 1293
    400 Marketing 1576
    500 Shipping 703
    600 Foreign Sales 129
  4. Der "Accountant" kann seine Abfrage erneut ausführen und sieht die neue Zeile nicht, da die Transaktion nicht beendet wurde.

    SELECT *
    FROM Departments
    ORDER BY DepartmentID;
    DepartmentID DepartmentName DepartmentHeadID
    100 R & D 501
    200 Sales 902
    300 Finance 1293
    400 Marketing 1576
    500 Shipping 703
  5. Der "Sales Manager" möchte gerne eine zweite Abteilung hinzufügen, die sich auf Verkaufsinitiativen für Großkunden konzentriert. Führen Sie die folgende Anweisung im Fenster des "Sales Managers" aus:

    INSERT INTO Departments
     ( DepartmentID, DepartmentName, DepartmentHeadID )
       VALUES( 700, 'Major Account Sales', 902 );

    Die Änderung des "Sales Managers" wird nicht blockiert, da der "Accountant" die Snapshot-Isolation benutzt.

  6. Der "Accountant" muss seine Snapshot-Transaktion beenden, um die Änderungen zu sehen, die der "Sales Manager" in der Datenbank festgeschrieben hat.

    COMMIT;
       SELECT * FROM Departments
       ORDER BY DepartmentID;

    Nun sieht der "Accountant" die Abteilung "Foreign Sales", nicht aber die Abteilung "Major Account Sales".

    DepartmentID DepartmentName DepartmentHeadID
    100 R & D 501
    200 Sales 902
    300 Finance 1293
    400 Marketing 1576
    500 Shipping 703
    600 Foreign Sales 129
  7. Um zu vermeiden, dass die SQL Anywhere-Beispieldatenbank geändert wird, sollten Sie die unvollständige Transaktion zurücksetzen, welche die Zeile "Major Account Sales" einfügt, und eine zweite Transaktion benutzen, um die Abteilung "Foreign Sales" zu löschen.

    1. Führen Sie die folgende Anweisung im Fenster des "Sales Managers" aus, um die letzte, unvollständige Transaktion zurückzusetzen:

      ROLLBACK;
    2. Führen Sie im Fenster "Sales Manager" die folgenden beiden Anweisungen aus, um die Zeile zu löschen, die Sie zuvor eingefügt haben, und diesen Vorgang festzuschreiben.

      DELETE FROM Departments
      WHERE DepartmentID = 600;
      COMMIT;