1
|
- Kursory i praca z kursorami, kursory jawne i niejawne, otwieranie
kursora, pobieranie z kursora, zamykanie kursora, wyjątki systemowe i
użytkownika, zgłaszanie i obsługa wyjątków
|
2
|
- Każde zapytanie SQL umieszczone w programie PL/SQL może zwrócić zero,
jedną bądź wiele krotek. Aby efektywnie przetworzyć krotki zwrócone
przez zapytanie korzystamy z kursorów. Kursor jest obiektem związanym z
zapytaniem. Programista może:
- Otworzyć kursor (zidentyfikować zbiór wynikowy)
- Pobrać daną do kursora (odczytać kolejną krotkę z wyniku zapytania i
wpisać ją do kursora)
- Zamknąć kursor (zwolnić obszar pamięci przydzielony kursorowi)
- Kursor to nazwa obszaru roboczego, w którym mieści się wynik zapytania
(result set). Wewnątrz kursora wyróżniamy bieżący wiersz (current row).
Kursor może być jawny (explicit) lub niejawny (implicit).
|
3
|
- Nazwa kursora nie jest zmienną, lecz identyfikatorem. Do kursora nie
można przypisać wartości
- Parametry są widoczne tylko wewnątrz kursora, nie można związać z nimi
żadnych ograniczeń
|
4
|
- Otwarcie kursora powoduje wykonanie związanego z nim zapytania i
zidentyfikowanie zbioru wynikowego, zawierającego krotki spełniające
kryteria wyszukiwania.
|
5
|
- Każde wykonanie polecenia FETCH powoduje odczytanie bieżącego wiersza
kursora i przesunięcie znacznika kursora na kolejny wiersz. Na liście
zmiennych musi się znajdować taka sama liczba zmiennych jak liczba
atrybutów w kursorze. Odpowiednie zmienne i atrybuty muszą się zgadzać
co do typu.
|
6
|
- Zamknięcie kursora powoduje, że kursor staje się nieaktywny a zbiór
wynikowy związany z kursorem staje się niezdefiniowany. Zamknięty kursor
można powtórnie otworzyć, np. z innymi parametrami. Każde odwołanie się
do zamkniętego (lub jeszcze nie otwartego) kursora powoduje błąd INVALID_CURSOR.
|
7
|
- %FOUND – wartością atrybutu jest TRUE jeśli ostatnia operacja FETCH
odczytała krotkę z kursora. W przeciwnym wypadku (tzn. kiedy odczyt się
nie udał) atrybut przyjmuje wartość FALSE. Przed pierwszym odczytem
atrybut ma wartość NULL
- %NOTFOUND – wartością atrybutu jest FALSE jeśli ostatnia operacja FETCH
odczytała krotkę z kursora. W przeciwnym wypadku (tzn. kiedy odczyt się
nie udał) atrybut przyjmuje wartość TRUE. Przed pierwszym odczytem
atrybut ma wartość NULL
- %ROWCOUNT – wartością atrybutu jest liczba odczytanych z kursora krotek.
Przed pierwszym odczytem atrybut ma wartość 0
- %ISOPEN – wartością atrybutu jest TRUE jeśli kursor jest otwarty i FALSE
jeśli kursor jest zamknięty.
|
8
|
- Każde polecenie DML (INSERT, UPDATE, DELETE, SELECT FOR UPDATE) powoduje
utworzenie kursora niejawnego (ang. implicit cursor). Dla takiego
kursora można sprawdzać wartości następujących atrybutów:
- SQL%ROWCOUNT: liczba wierszy zmodyfikowanych przez polecenie
- SQL%FOUND: TRUE jeśli ostatnie polecenie zmodyfikowało jakiekolwiek
wiersze
- SQL%NOTFOUND: TRUE jeśli ostatnie polecenie nie zmodyfikowało żadnych
wierszy
- SQL%ISOPEN: zawsze FALSE (kursor niejawny jest zamykany natychmiast po
zakończeniu polecenia)
|
9
|
|
10
|
- Zmienna sterująca pętlą jest deklarowana automatycznie jako zmienna
typu kursor%ROWTYPE
- Kursor jest otwierany automatycznie
- W każdym przebiegu pętli jedna krotka jest pobierana z kursora i
umieszczana w zmiennej sterującej pętlą
- Po pobraniu ostatniej krotki kursor jest automatycznie zamykany
|
11
|
- Zmienna sterująca pętlą jest deklarowana automatycznie jako zmienna
typu podzapytanie%ROWTYPE
- Kursor jest otwierany automatycznie
- W każdym przebiegu pętli jedna krotka jest pobierana z kursora i
umieszczana w zmiennej sterującej pętlą
- Po pobraniu ostatniej krotki kursor jest automatycznie zamykany
- Kursor oparty na podzapytaniu nie może być parametryzowany ani
wykorzystywany wielokrotnie
|
12
|
- Klauzula WHERE CURRENT OF ma zastosowanie do poleceń UPDATE i DELETE
umieszczonych wewnątrz kursora. Warunek jest spełniony tylko i wyłącznie
dla bieżącej krotki w kursorze. Aby można było skorzystać z tej
klauzuli, zapytanie definiujące kursor musi zawierać klauzulę FOR UPDATE
OF (założenie blokady na odczytywanych krotkach)
|
13
|
- Błąd lub ostrzeżenie nazywamy w PL/SQL wyjątkiem (ang. exception).
Wyjątki mogą być systemowe (dzielenie przez zero, brak wolnej pamięci,
brak praw do obiektu) lub definiowane przez użytkownika (za niski
budżet, za wysoka płaca, zbyt mała ilość towaru w magazynie).
- Wystąpienie błędu jest sygnalizowane przez wywołanie wyjątku. Błędy
systemowe sygnalizowane są automatycznie, błędy definiowane przez
użytkownika są wywoływane ręcznie za pomocą polecenia RAISE.
- Po wystąpieniu wyjątku kontrola przechodzi do procedury obsługi wyjątku (ang.
exception handler). Po jej wykonaniu kontrola przechodzi do kolejnego
bloku nadrzędnego. Jeśli procedura obsługi danego błędu nie zostanie
znaleziona, to wykonywanie programu zostanie przerwane.
|
14
|
- Sekwencja poleceń i zostaje wykonana, gdy w bloku wystąpi wyjątek i.
- Nieobsłużony wyjątek przerywa działanie programu.
- Opcjonalna sekcja OTHERS – obsługuje wszystkie niewymienione wyjątki.
|
15
|
|
16
|
|
17
|
|
18
|
- Wyjątki mogą być deklarowane w sekcji deklaracji dowolnych bloków
PL/SQL. Przed użyciem wyjątku musi on być zadeklarowany. Wyjątek jest
widoczny w danym bloku i wszystkich jego blokach podrzędnych.
- Wyjątek nie jest daną, do wyjątku nie można przypisać żadnej wartości
ani użyć wyjątku w jakiejkolwiek operacji arytmetycznej.
|
19
|
- Użytkownik może wywoływać ręcznie zarówno błędy systemowe, jak i
zdefiniowane przez siebie. Każdy wywołany błąd powinien zostać obsłużony
przez odpowiednią procedurę obsługi wyjątku.
|
20
|
- Funkcja SQLCODE zwraca numer błędu, który wystąpił. Numer jest zawsze
ujemny, za wyjątkiem błędu NO_DATA_FOUND (+100) i błędów definiowanych
przez użytkownika (+1)
- Funkcja SQLERRM zwraca treść błędu, który wystąpił.
- Jeśli nie wystąpił żaden błąd to SQLCODE zwraca 0 a SQLERRM zwraca : „ORA-0000:
normal, successful completion”
|
21
|
- Procedura pozwala na przesyłanie komunikatów o błędach zdefiniowanych
przez użytkownika do programu nadrzędnego.
- error_numer: liczba ujemna z przedziału –20000 ¸ -20999
- message: łańcuch znaków o rozmiarze do 2048 bajtów
- TRUE, FALSE: czy błąd ma być umieszczony na szczycie stosu błędów, czy
też ma je zastąpić
|