Die Blockstruktur von PL/SQL

PL/SQL ist in sogenannten Blöcken strukturiert und beinhaltet konditionale Befehle, Schleifen und Verzweigungen, um den Programmablauf zu kontrollieren. Variablen können lokal definiert werden (scoped), um sie nur innerhalb des Blockes sichtbar zu machen, in dem sie definiert wurden.

Es gibt drei Arten von PL/SQL Blöcken: anonyme Blöcke, benannte Prozeduren und benannte Funktionen. All diese Blöcke teilen sich fast alle Blockeigenschaften, so daß wir diese Eigenschaften vorerst für alle Blockarten beschreiben.

Ein anonymer Block ist eine unbenannte Prozedur, sie kann nicht aufgerufen werden. Normalerweise ist sie an einen Trigger oder ein Applikationsereignis (z.B. in ORACLE Forms) gebunden.

Eine benannte Prozedur kann aufgerufen werden, kann Parameter übernehmen, gibt aber nicht explizit einen Wert zurück.

Eine benannte Funktion kann auch aufgerufen werden, Parameter (sog. Argumente) übernehmen und liefert im Gegensatz zu einer Prozedur immer einen Wert zurück.

Struktur

Die Struktur eines anonymen Blockes sieht wie folgt aus

DECLARE 
-- (optional, wenn keine Variablen genutzt werden) 
-- Definition von allen Variablen und Objekten, die innerhalb des Blocks 
-- genutzt werden 
BEGIN 
-- Die Befehle, die den Block ausmachen (mind. eine ausführbare Anweisung) 
EXCEPTION 
-- (optional, wenn keine Fehlerbehandlung erfolgt) 
-- Alle Exception-Handler, die der Fehlerbehandlung dienen 
END; -- Ende des Blocks

Minimalform

Die minimale Form eines anonymen Blockes ist also folgende:

BEGIN
  NULL; 
END;

Dieser Block tut nichts und wird daher immer erfolgreich beendet werden. Der DECLARE-Teil ist optional, wenn keine Variablen-Deklaration erfolgt, kann er weggelassen werden. Der ausführbare Teil, der hinter BEGIN beginnt, muß mindestens eine ausführbare Anweisung enthalten, hier NULL (vgl. NOP, oder no operation). Eine Fehlerbehandlung erfolgt nicht (was soll auch für ein Fehler auftreten?), daher kein EXCEPTION-Teil.

Komplexeres Beispiel

Ein komplexeres Beispiel sehen wir hier, ohne es kommentieren zu wollen:

Beispiel:

DECLARE    
  TEMP_COST NUMBER(10,2); 
BEGIN    
  SELECT COST INTO TEMP_COST FROM JD11.BOOK WHERE ISBN = 21;
IF TEMP_COST > 0 THEN
  UPDATE JD11.BOOK SET COST = (TEMP_COST*1.175) WHERE ISBN = 21;
ELSE
  UPDATE JD11.BOOK SET COST = 21.32 WHERE ISBN = 21;    
END IF;     
COMMIT; 
EXCEPTION    
  WHEN NO_DATA_FOUND THEN       
       INSERT INTO JD11.ERRORS (CODE, MESSAGE) VALUES(99, 'ISBN 21 NOT FOUND'); 
END;

Grundregeln

Einige Regeln zur Arbeit mit Blöcken und deren Struktur wollen wir bereits hier definieren:

Jede PL/SQL-Einheit muß eine Block-Struktur haben. Minimal sind also die Schlüsselworte BEGIN und END um die ausführbaren Anweisungen zu stellen.

SELECT Befehle innerhalb vom PL/SQL Blöcken sind embedded SQL (eine ANSI Kategorie) und müssen als solche exakt eine Zeile zurückliefern. SELECT Befehle, die mehr als eine Zeile oder keine Zeile liefern, lösen einen Fehler aus. Wenn Sie mit einer Reihe von Datensätzen arbeiten müssen, plaziert man die Menge von Datensätzen in einen Cursor. Das Schlüsselwort INTO bei SELECT Statements in PL/SQL (außer bei der Arbeit mit Cursors) ist Pflicht, denn der gelieferte Wert muß in einer Variablen gespeichert werden.

Wenn innerhalb eines PL/SQL Blocks Variablen oder Objekte genutzt werden, müssen diese im DECLARE Teil bekannt gemacht werden (hier gibt es Ausnahmen)

Wenn ein EXCEPTION Teil existiert, wird der jeweilige Exception-Handler nur aufgerufen, wenn der entsprechende Fehler im ausführbaren Teil auftritt. Wenn der Fehlerbehandlungsteil bearbeitet wurde, wird die Bearbeitung des gesamten Blocks abgeschlossen. Ein Fehler im Fehlerbehandlungsteil führt zum „Hochreichen“ des Fehlers an den Aufrufer des Blocks.

PL/SQL Blöcke können geschachtelt (und damit sehr mächtig) werden. Die Schachtelung kann überall da erfolgen, wo eine ausführbare Anweisung stehen kann (also auch im Exception-Teil, nicht jedoch im Declare-Teil).

Schreibe einen Kommentar

Deine E-Mail-Adresse wird nicht veröffentlicht. Erforderliche Felder sind mit * markiert.