Integritätsprüfung

Ziel der Integritätsprüfung ist die persistente Speicherung nur von semantisch korrekten Daten in der Datenbasis. Sie werden auch konsistente Daten genannt, und genügen allen im DBS definierten Integritätsbedingungen.

Zu diesem Zweck stehen in SQL und bei Oracle im wesentlichen zwei Konzepte zur Verfügung:

ASSERTIONS

Das Konzept der ASSERTIONS wird hier aufgrund der fehlenden Implementierungen nicht weiter vertieft. Es ist jedoch hinsichtlich der Prüfungszeitpunkte IMMEDIATE und DEFERRED sowie dem Rückgängigmachen im Fehlerfall analog zu dem der CONSTRAINTS zu sehen.

CONSTRAINTS

Als CONSTRAINTS stehen die Bedingungen: Primärschlüssel (PRIMARY KEY), Zweitschlüssel (UNIQUE), Fremdschlüssel (FOREIGN KEY), Pflichteingabe (NOT NULL) und CHECK-Bedingungen zur Verfügung.
Constraints können aktiviert sein (enabled) oder auch deaktiviert (disabled). Den Integritätsbedingungen der CONSTRAINTS ist gemeinsam, dass es statische Integritätsbedingungen sind. Aufgrund der starken Einschränkung beim CHECK-CONSTRAINT, das überhaupt keine SELECT-Anfragen, weder auf die eigene Tabelle noch auf andere Tabellen zulässt, stoßen die CONSTRAINS sehr schnell an ihre semantischen Grenzen. Abhilfe können da TRIGGER schaffen. (u.s.)

Ist ein Constraint angelegt und/oder aktiviert, so steht mit absoluter Gewissheit die Konsistenz der Daten fest, denn beim Anlegen und/oder Aktivieren wird immer das Constraint für die bereits gespeicherten Daten geprüft. Und es läßt sich nur angelegen und/oder aktivieren, wenn alle persistent gespeicherten Daten geprüft und als korrekt befunden worden sind (rückblickende Kontrolle). Ist ein Constraint aktiv, so wird diese Bedingung für zukünfitig eintretenden, relevanten Datenmanipulationen (INSERT, UPDATE, DELETE?) ausgewertet und wenn das Ergebnis TRUE oder UNKNOWN ist, wird die Änderung akzeptiert.
Und nur für den Fall, dass die Bedingung zu FALSE ausgewertet wird, wird ein Fehler gemeldet und die Datenmanipulation zurückgewiesen (dreiwertige Logik). Das UNKNOWN wie TRUE gehandhabt wird, hat seinen Ursprung darin, dass die CONSTRAINTS auch für leere Tabellen erfüllt sein müssen bzw. für leere Spalten. Es sei hier darauf hingewiesen, das es sich bei SELECT-Bedingungen anders verhält. Dort wird UNKNOWN wie FALSE (falsch) gehandelt.

Eine Integritätsprüfung kann IMMEDIATE (sofort) oder DEFERRED (verzögert) erfolgen. Mit DEFERRED wird die Prüfung der Integritätsbedingung zum Ende der Transaktion bezeichnet. IMMEDIATE beschreibt die Prüfung unmittelbar im Anschluss an die Ausführung einer einzelnen Manipulationsanweisung (INSERT, UPDATE, DELETE?). COMMIT beendet eine Transaktion und löst damit eine DEFERRED-Integritätsprüfung aus. Diese unterschiedlichen Prüfungszeitpunkte bedingen zwei unterschiedliche Reaktionen im Fehlerfall. Wird ein Integritätsfehler bei der IMMEDIATE-Prüfung erkannt, so wird nur die letzte, also die fehlerfahfte Manipulationsanweisung rückgängig gemacht. Wird hingegen ein Integritätsfehler bei der DEFERRED-Prüfung erkannt, so wird die gesamte Transaktion zurückgerollt, also implizit ein ROLLBACK ausgeführt. Grund für dieses unterschiedliche Verhalten ist einmal das Atomaritätsprinzip? von Transaktionen und zum anderen das Problem, dass am Ende einer Transaktion nicht immer eindeutig vom DBS entschieden werden kann, welche Manipulationsanweisung nun die fehlerverursachende war.

Syntax der Integritätsprüfungszeitpunkte <CONSTRAINT Characteristika>:

    <CONSTRAINT Characteristika> ::=
         { INITIALLY DEFERRED | INITIALLY IMMEDIATE } [ [ NOT ] DEFERRABLE ]

Sie können unabhängig davon definiert werden, ob das CONSTRAINT als Tabellenbedingung oder als Spaltenbedingung speifiziert ist. CONSTRAINT Characteristika können über die SET-CONSTRAINTS-Anweisung verändert werden.

ROLLBACK beendet zwar auch eine Transaktion, jedoch indem sie rückgängig gemacht wird. Eine Integritätsprüfung ist daher unnötig und wird nicht ausgeführt. DDL-Anweisungen (CREATE, ALTER, DROP) beinhalten ein implizites COMMIT, was dafür sorgt, dass jede DDL-Anweisung unmittelbar in die DICTIONARY-Tabellen eingetragen wird. Dieses implizite COMMIT hat zur Folge, dass DDL-Anweisungen immer auch eine Transaktion beenden und eine DEFERRED-Integritätsprüfung auslösen. SELECT-Anweisungen sind in diesem Zusammenhang unkritische Aktionen, die keine Prüfung erfordern: Es soll ja nichts gespeichert werden, sondern nur angezeigt.

TRIGGER

TRIGGER haben gegenüber den CONSTRAINTS einmal den Vorteil, einer fast beliebigen Semantik, da ihnen im Aktionsteil der TRIGGER der fast komplette SQL- und PL/SQL-Befehlsumfang? zur Verfügung steht. Einzige Einschränkung sind Befehle wie COMMIT, ROLLBACK sowie CREATE, ALTER, DROP mit ihren impliziten COMMITS, da in TRIGGERN selbst keine Transaktionssteuerungsbefehle zugelassen sind, was mit ihrem Ausführungsmodell zusammenhängt.
Anders als bei den statischen Integritätsbedingungen der CONSTRAINTS, sind mit TRIGGERN sehr einfach auch dynamische, transitionale Bedingungen formulier- und prüfbar. Für dynamische, temporale? Bedingungen wird es schon aufwändiger, aber sie lassen sich auch mit TRIGGERN prüfen.

Der fast komplette SQL- und PL/SQL-Befehlsumfang im Aktionsteil hat einen weiteren Vorteil zur Folge, eine beliebige Programmierung der Reaktionen auf Fehler. So sind im Aktionstiel des Trigger auch Fehlerkorrekturen, Protolollierungen, etc. nach belieben programmierbar.

Eine Einschränkung der TRIGGER gegenüber den CONSTRAINTS ist beim Prüfungszeitpunkt zu finden. Da es keine TRIGGER gibt, die zum COMMIT-Zeitpunkt feuern (DEFERRED), steht bei der TRIGGER-Prüfung nur der IMMEDIATE-Zeitpunkt zur Verfügung.

Einen weiteren Nachteil gibt es noch, die oben beschriebene "rückblickende Kontrolle" bei CONSTRAINTS gibt es bei TRIGGERN nicht. Bei Integritätsbedingungen mit TRIGGERN gibt es nicht diese 100%-Sicherheit, was die Konsistenz der Daten angeht. Sie werden nicht für bestehende Daten ausgeführt, sondern nur für zukünftig eintretende Ereignisse. Dieses Problem gilt für neu programmierte TRIGGER gleichermaßen wie für TRIGGER die deaktiviert (disabled) und wieder aktiviert werden (enabled).
Dass die Konsistenz der alten Daten auch geprüft wird, muss dann der Entwickler gewährleisten, entweder durch entsprechende Prüfprogramme oder für den Fall, dass es einen Prüf-TRIGGER für das UPDATE-Ereignis gibt, mit einer UPDATE-Anweisung, die nichts verändert, wohl aber für alle bestehenden Daten ausgeführt wird. Somit wird dann der Prüf-TRIGGER für alle Daten einmal ausgeführt und kontrolliert deren Semantik.

Quellen:

  • ANSI/ISO/IEC 9075-1:2003. Part 1 "SQL/Framework", ISO International Organization for Standardization / ANSI American National Standards Institute, September 2003
  • ANSI/ISO/IEC 9075-2:2003. Part 2 "SQL/Foundation", ISO International Organization for Standardization / ANSI American National Standards Institute, Dezember 2003
  • Elmasri, Ramez/Navathe, Shamkant B.: "Grundlagen von Datenbanksystemen" , Pearson Studium, München, 2002, ISBN 3-8273-7021-3
  • Faeskorn-Woyke, Heide/Bertelsmeier, Birgit/Riemer, Petra/Bauer, Elena: "Datenbanksysteme - Theorie und Praxis mit SQL2003, Oracle und MySQL", Pearson Education, München, 2007, ISBN 978-3-8273-7266-6
  • Kemper, Alfons/Eickler, André: "Datenbanksysteme", Oldenbourg, München, 2009, 978-3-486-59018-0
  • Melton, Jim/Simon, Alan R.: "SQL: 1999 - Understanding Relational Language Components", Morgan Kaufmann, San Francisco, 2001, ISBN 1558604561
  • Oracle® Database SQL Language Reference 11g Release 2 (11.2), E17118-03, August 2010, http://download.oracle.com/docs/cd/E11882_01/server.112/e17118.pdf
  • Saake, Gunter/Sattler, Kai-Uwe/Heuer, Andreas: "Datenbanken - Konzepte und Sprachen", mitp-Verlag, Redline GmbH, Heidelberg, 2007, ISBN 3-8266-1664-2
  • Vossen, Gottfried: "Datenmodelle, Datenbanksprachen und Datenbankmanagementsysteme", Oldenbourg, München, 2008, ISBN 978-3-486-27574-2

Kategorien: Aktive Datenbanken, SQL, Transaktionen, I