CATEGORII DOCUMENTE |
Obiective :
Dupa terminarea acestei prezentari veti fi in stare sa realizati urmatoarele :
- definirea exceptiilor PL/SQL
- recunoasterea exceptiilor netratate
- afisarea si folosirea diferitelor tipuri de tratari ale exceptiilor in PL/SQL
- detectarea erorilor neanticipate
- descrierea efectelor propagarii exceptiilor in blocuri imbricate
- modificarea in functie de necesitati a mesajelor de exceptie ale PL/SQL
Scopul prezentarii :
In aceasta prezentare veti invata ce sunt exceptiile PL/SQL si cum se poate lucra cu ele folosind tratari predefinite, non-predefinite, si definite de utilizator .
Tratarea exceptiilor in PL/SQL
Ce este o exceptie ?
- Un identificator in PL/SQL care apare in timpul unei executii.
Cum apare ?
- La aparitia unei erori.
- Este apelata explicit.
Cum se trateaza ?
Este capturata intr-o rutina de tratare a exceptiei.
- Este propagata spre mediul apelant.
O exceptie este un identificator in PL/SQL , care apare in timpul executiei unui bloc care isi incheie partea principala de instructiuni. Un bloc se termina intodeauna cand PL/SQL genereaza o exceptie, dar pot fi specificate rutine utilizator de tratare a acestora in care se pot executa actiuni finale.
Exista doua metode pentru generarea unei exceptii :
- O eroare ORACLE apare si exceptia asociata este generata automat. De exemplu, daca eroarea ORA-01403 apare cand nici o linie nu este returnata dintr-o tabela ca urmare a unei instructiuni SELECT, atunci PL/SQL genereaza exceptia NO_DATA_FOUND.
- Utilizatorul genereaza explicit o exceptie introducand instructiunea RAISE in interiorul blocului. Exceptia generata poate fi fie definita de utilizator, fie predefinita.
Capturarea exceptiei Propagarea exceptiei
Este generata Este generata
exceptia exceptia
Exceptia este Exceptia nu este
capturata capturata
Exceptia se propaga in mediul apelant
Capturarea unei exceptii
Daca exceptia este generata in partea executabila a blocului, programul sare in rutina de tratare corespunzatoare din sectiunea de bloc alocata exceptiilor. Daca PL/SQL trateaza cu succes exceptia atunci aceasta nu se propaga in blocul superior. Blocul PL/SQL se termina cu succes.
Propagarea unei exceptii
Se poate trata o exceptie prin propagarea ei spre mediul apelant. Daca exceptia este generata in portiunea executabila a blocului si nu exista nici o rutina de tratare corespondenta atunci blocul PL/SQL se termina cu eroare.
Tipuri de exceptii
Predefinite ale ORACLE Generate implicit
Non-predefinite ale ORACLE
Definite de utilizator Generate explicit
Exceptiile se pot programa pentru a evita intreruperile din program. Exista trei tipuri :
Exceptie |
Descriere |
Modul tratarii |
Eroare predefinita ORACLE |
Una din cele aproximativ 20 de erori care apar cel mai des in PL/SQL |
Nu se declara. Se lasa sa fie generata implicit de ORACLE |
Eroare non-predefinita ORACLE |
Oricare alta eroare standard ORACLE |
Se declara in sectiunea declarativa. Se lasa sa fie generata implicit de ORACLE |
Eroare definita de utilizator |
O conditie pe care utilizatorul o considera anormala |
Se declara in sectiunea decla-rativa. Se genereaza explicit. |
Capturarea exceptiilor
Sintaxa
EXCEPTION
WHEN exception1 [ OR exception2 . . .] THEN
statement1;
statement2;
. . .
[ WHEN exception3 [ OR exception4 . . .] THEN
statement1;
statement2;
. . . ]
[ WHEN OTHERS THEN
statement1;
statement2;
. . . ]
Se poate captura orice eroare prin includerea unei rutine corespunzatoare in cadrul sectiunii de tratare a exceptiilor dintr-un bloc PL/SQL . Fiecare tratare consta intr-o clauza WHERE , care specifica exceptia, urmata de o secventa de instructiuni care vor fi executate cand exceptia este generata.
In cadrul sintaxei,
exception este numele standard a unei exceptii predefinite sau numele unei exceptii definite de utilizator si declarata in cadrul sectiunii declarative
statement reprezinta una sau mai multe instructiuni ale PL/SQL sau SQL
OTHERS este o tratare de exceptii optionala si trateaza clauze care captureaza exceptiile nespecificate
Tratarea exceptiilor WHEN OTHERS
Sectiunea de tratare a exceptiilor captureza numai acele exceptii care au fost specificate ; orice alte exceptii nu sunt capturate decat daca se foloseste tratarea cu OTHERS. Aceasta captureaza orice expresie care nu a fost inca tratata. Din acest motiv OTHERS este ultima tratare definita.
Tratarea OTHERS captureaza toate expresiile care nu au fost tratate. Cateva instrumente ORACLE au propriile exceptii predefinite care pot fi generate de utilizator pentru provocarea anumitor evenimente in aplicatii. Aceste exceptii sunt de asemenea capturate de OTHERS.
Observatii asupra tratarii exceptiilor :
- se incepe sectiunea de tratare a exceptiilor dintr-un bloc cu EXCEPTION.
- se pot defini mai multe rutine pentru un bloc, fiecare cu actiunile ei specifice.
- cand este generata o exceptie, PL/SQL proceseaza doar o rutina inainte de a parasi blocul.
- clauza OTHERS trebuie plasata dupa toate clauzele de tratare a exceptiilor.
Captarea erorilor predefinite ale serverului de ORACLE
O eroare predefinita poate fi capturata prin asignarea numelui ei cu o rutina de
tratare corespunzatoare.
Pentru o lista completa a erorilor predefinite vezi PL/SQL User's Guide and Reference, Release 8, "Error Handling".
NOTA : PL/SQL declara exceptiile predefinite in pachetul STANDARD.
Este un lucru extrem de util sa tratam intotdeauna exceptiile NO_DATA_FOUND si TOO_MANY_ROWS care sunt cele mai intalnite.
Exceptii predefinite :
Numele exceptiei |
No. Exceptiei |
Descriere |
ACCESS_INTO_NULL |
ORA-06530 |
Se incearca asignarea unei valori unui obiect neinitializat |
COLLECTION_IS_NULL |
ORA-06531 |
Se incearca aplicarea unei metode de tip collection alta decat EXISTS unei tabele imbricate sau varray |
CURSOR_ALREADY_OPEN |
ORA-06511 |
Se incearca deschiderea unui cursor deja deschis |
DUP_VAL_ON_INDEX |
ORA-00001 |
Se incearca introducerea unei valori duplicat |
INVALID_CURSOR |
ORA-01001 |
Operatiune ilegala asupra unui cursor |
INVALID_NUMBER |
ORA-01722 |
Esec in conversia unui string in numar |
LOGIN_DENIED |
ORA-01017 |
Nume utilizator neexistent sau parola incorecta la login |
NO_DATA_FOUND |
ORA-01403 |
SELECT nu intoarce nici o data |
NOT_LOGGED_ON |
ORA-01012 |
PL/SQL apeleaza o baza de date fara a fi conectat la server |
PROGRAM_ERROR |
ORA-06501 |
PL/SQL are o problema interna |
ROWTYPE_MISMATCH |
ORA-06504 |
Variabila cursor gazda si cursorul PL/SQL intorc tipuri diferite |
STORAGE_ERROR |
ORA-06500 |
PL/SQL nu mai are memorie sau aceasta este corupta |
SUBSCRIPT_BEYOND_COUNT |
ORA-06533 |
Apelarea unei tabele sau varray folosind un numar de index mai mare decat numarul elementelor obiectului. |
SUBSCRIPT_OUTSIDE_LIMIT |
ORA-06532 |
Apelarea unei tabele sau varray folosind un numar de index care este incorect (ex : -1) |
TIMEOUT_ON_RESOURCE |
ORA-00051 |
Apare time-out in timp ce ORACLE asteapta o resursa |
TOO_MANY_ROWS |
ORA-01422 |
SELECT intoarce mai mult de o coloana |
VALUE_ERROR |
ORA-06502 |
Eroare de tip aritmetic, trunchiere, conversie, sau de constrangere de marime |
ZERO_DIVIDE |
ORA-01476 |
Incercare de impartire la 0 |
Exceptii Predefinite
Sintaxa :
BEGIN
SELECT . . .;
EXCEPTION
WHEN NO_DATA_FOUND THEN
statement1;
statement2;
WHEN TOO_MANY_ROWS THEN
statement1;
WHEN OTHERS THEN
statement1;
statement2;
statement3;
END;
Captarea Erorilor Non-Predefinite ale Serverului Oracle
Sectiunea declarativa Sectiunea de tratare
a exceptiei
Se denumeste Se programeaza Se trateaza exceptia
exceptia PRAGMA_EXCEPTION_INIT
Captarea erorilor Non-Predefinite ale Serverului Oracle
Se poate captura o eroare non-predefinita fie prin a o declara sau prin folosirea handlerului OTHERS. Exceptia declarata este generata implicit. In PL/SQL, constrangerea (PRAGMA) EXCEPTION_INIT comanda compilatorului sa asocieze numele unei exceptii cu un numar de exceptie ORACLE. Acest lucru permite ca sa putem referi orice exceptie interna cu numele ei si sa o putem trata intr un handler specific.
Nota : PRAGMA (denumita si pseudoinstructiune) este cuvantul care semnifica faptul ca expresia este o directiva compilator, care nu este procesata cand se executa un bloc PL/SQL. Mai mult, ea spune compilatorului PL/SQL sa interpreteze toate aparitiile din cadrul blocului a exceptiei numite ca fiind numarul de eroare asociat de serverul ORACLE.
Captarea unei exceptii Non-predefinite a serverului Oracle
1. Se declara numele exceptiei in sectiunea declarativa.
Sintaxa :
exception EXCEPTION;
unde exception este numele exceptiei.
2. Asocierea exceptiei declarate cu numarul standard de eroare a serverului de Oracle folosind instructiunea PRAGMA EXCEPTION_INIT.
Sintaxa :
PRAGMA EXCEPTION_INIT(exception, error_number);
unde exception este exceptia declarata anterior
error_number este numarul standard de eroare a serverului Oracle.
3. Se asociaza exceptia declarata cu rutina de tratare corespunzatoare.
Captarea exceptiilor definite de utilizator
Sectiunea declarativa Sectiunea executabila Sectiunea de tratare
Se numeste exceptia Se apeleaza explicit exceptia Se trateaza exceptia
Exceptiile definite de utilizator
Exemplu :
Captarea exceptiilor definite de utilizator :
Se capteaza o exceptie definita de utilizator declarand exceptia si apeland-o explicit.
1. Se declara numele pentru exceptia utilizator in cadrul sectiunii declarative.
Sintaxa :
exception EXCEPTION;
unde exception este numele exceptiei.
2. Folosind instructiunea RAISE se apeleaza explicit exceptia in sectiunea executabila.
Sintaxa :
RAISE exception;
unde exception este exceptia definita anterior.
3. Se creaza o referinta la exceptia declarata in cadrul sectiunii executabile.
In exemplul de mai sus : Acest client are o 'regula' de afaceri care spune ca un produs nu poate fi sters din baza de date daca mai exista inventar din acest produs in stoc. Cum nu exista nici o constrangere care sa reglementeze acest lucru, se trateaza evenimentul explicit in cadrul aplicatiei. Inainte de executarea unui DELETE in tabela PRODUCT, blocul interogheaza tabela INVENTORY sa verifice daca exista stoc pentru produsul respectiv. Daca da, se apeleaza exceptia.
Functii de captare a erorilor
Cand apare o exceptie , se poate identifica codul de eroare asociat sau mesajul de eroare folosind doua functii. In functie apoi de valoarea codului sau de mesaj se pot decide masurile aferente care vor trebui luate.
SQLCODE intoarce numarul de eroare Oracle pentru exceptiile interne. Se poate transmite numarul erorii functiei SQLERRM, care returneaza apoi mesajul asociat cu numarul erorii.
Functia |
Descriere |
SQLCODE |
Returneaza valoarea numerica pentru codul erorii ( se poate asigna unei variabile d etip NUMBER ). |
SQLERRM |
Returneaza data de tip sir de caractere continand mesajul asociat cu numarul erorii. |
Exemple de valori ale SQLCODE :
Valori SQLCODE |
Descriere |
Nu s-a intalnit nici o exceptie |
|
Exceptie definita de utilizator |
|
Exceptia NO_DATA_FOUND |
|
numar negativ |
Alt numar de eroare al serverului Oracle |
Functii de captare a exceptiilor :
Cand o exceptie este captata in sectiunea WHEN OTHERS, se poate folosi un set de functii generice pentru identificarea acestor erori.
In exemplu se prezinta asignarea valorilor SQLCODE si SQLERRRM unor variabile care ai apoi sunt folosite in instructiuni SQL.
Mediile apelante
SQL*PLUS |
Afiseaza mesajul si numarul de eroare pe ecran |
Procedure Builder |
Afiseaza mesajul si numarul de eroare pe ecran |
Developer/2000 Forms |
Acceseaza mesajul si numarul de eroare prin pachetul de functii ERROR_CODE si ERROR_TEXT |
Precompilarea aplicatiilor |
Acceseaza numarul exceptie direct prin structura de date SQLCA |
Un bloc final(imbricat) PL/SQL |
Capturarea exceptiei in rutina de tratare a exceptiei in blocul final (imbricat) |
In loc de capturarea unei exceptii in cadrul blocului PL/SQL, se permite transmiterea exceptie mediului apelant pentru a o trata. Fiecare mediu apelant are propriul mod de afisare si accesare a erorilor.
Sub-blocurile pot trata o exceptie
sau o pot transmite blocului
final(imbricat)
Cand un sub-bloc trateaza o exceptie, el se termina normal, si controlul se preia automat de blocul final(imbricat) dupa expresia END a subbocului.
In orice caz, daca in PL/SQL apare o exceptie si blocul curent nu are o solutie pentru aceasta, exceptia parcurge succesiv blocuri finale(imbricate) pana gaseste o tratare a ei. Daca nici unul dintre blocuri nu trateaza exceptia, apare ca rezultat o exceptie netrata in mediul curent.
Cand exceptia parcurge un bloc final(imbricat), actiunile ramase de executat in acest bloc sunt ocolite(sarite).
Un avantaj al acestui comportament este ca se pot include expresii care necesita propriile tratari a erorilor din blocurile in care se gasesc, permitand tratarea mai general a exceptiei in blocul final(imbricat).
Sintaxa :
raise_application_error ( error_number,
message [ , ] ) ;
- o procedura care permite sa emiti mesaje de eroare definite de utilizator din
subprogramele stocate.
- se apeleaza numai din executia(executabilul) subprogramului stocat.
Procedura RAISE_APPLICATION_ERROR se foloseste interactiv pentru comunicarea unei exceptii predefinite prin returnarea unui cod de eroare nestandar si a unui mesaj de eroare. Cu RAISE_APPLICATION_ERROR se pot prezenta erorile dintr-o anume aplicatie si se poate evita returnarea unei exceptii netratate.
In cadrul sintaxei:
- error number este un specificator de numar pentru exceptia cuprinsa intre
-20000 si -20999
- message este un mesaj specificat de utilizator pentru exceptie. Este un sir de caractere de 2048 biti lumgime.
- TRUE | FALSE este un parametru Boolean optional. Daca este TRUE, atunci eroarea se afla in lista(stiva) erorilor precedente. Daca este FALSE, eroarea va inlocui toate erorile anterioare.
Exemplu :
. . .
EXCEPTION
WHEN NO_DATA_FOUND THEN
RAISE_APPLICATION_ERROR_( -20201 ,
' Manager-ul nu este un angajat valid . ' ) ;
END ;
RAISE_APPLICATION_ERROR se utilizeaza in doua locuri diferite :
- sectiunea de executie
- sectiunea exceptiei
RAISE_APPLICATION_ERROR intoarce conditiile de eroare in conformitate cu erorile Server-ului Oracle.
Exemplu :
. . .
DELETE FROM emp
WHERE mgr = v_mgr ;
IF SQL%NOTFOUND THEN
RAISE_APPLICATION_ERROR ( -20202 , ' Acesta nu este un manager
valid ' ) ;
END IF ;
. . .
Sumar :
Tipuri de exceptii :
- erori predefinite de Server-ul Oracle
- erori nepredefinite de Server-ul Oracle
- erori definite de utilizator
Capturarea exceptiilor
Tratarea exceptiilor :
- capturarea exceptiilor in interiorul unui bloc PL/SQL
- propagarea exceptiei
Exercitii :
In aceste exercitii trebuie sa tratati exceptii pentru situatii specifice.
Scrieti un bloc PL/SQL care sa selecteze numele angajatului cu o valoare data a salariului :
a. Daca salariul introdus returneaza mai mult de un rand, tratati exceptia cu o exceptie tratata asemanatoare si introduceti in tabloul MESSAGES, mesajul " Mai mult de un angajat cu salariul < salariu > ".
b. Daca salariul introdus nu returneaza nici un rand, tratati exceptia cu o exceptie tratata asemanatoare si introduceti in tabloul MESSAGES, mesajul " Nu este nici un angajat cu salariul < salariu > ".
c. Daca salariul introdus returneaza numai un rand, introduceti in tabloul MESSAGES numele angajatului si valoarea salariului.
d. Tratati orice alta exceptie cu o exceptie tratata asemanatoare si introduceti in tabloul MESSAGES, mesajul " S-au mai produs alte erori ".
e. Testati blocul pentru mai multe cazuri ( situatii ).
RESULTS More than one employee with a salary of 3000 No employee with a salary of 6000
SMITH - 800
Creati un bloc PL/SQL care sa actualizeze locatia pentru un departament existent. Salvati blocul PL/SQL intr-un fisier.
a) Folositi o variabila citita de la tastatura pentru numarul departamentului.
b) Introduceti de la tastatura locatia departamentului.
c) Tratati cazul in care departamentul introdus nu exista in tabela.
d) Testati blocul PL/SQL.
e) Afisati numarul departamentului, numele departamentului si locatia pentru departamentul actualizat sau mesajul de eroare.
Please enter the departament number : 50 Please enter the departament location : HOUSTON PL/SQL procedure successfully completed. G_MESSAGE Departament 50 is an invalid department
Scrieti un bloc PL/SQL care tipareste numele angajatilor care au cu 100$ mai mult sau mai putin la salar fata de valoarea salariului introdus :
a. Daca nu este nici un angajat al carui salar sa se incadreze in acesta valoare, tipariti un mesaj utilizatorului indicandu-i acest lucru. Folositi o exceptie pentru acest caz.
b. Daca sunt unul sau mai multi angajati ale caror salarii se incadreaza in acesta valoare, mesajul va trebui sa indice cati angajati au un salar ce se incadreaza in valoarea respectiva.
c. Tratati orice alta exceptie cu o exceptie asemanatoare, mesajul va trebui sa indice daca au mai aparut si alte erori.
Please enter the salary : 800 PL/SQL procedure successfully completed. G_MESSAGE There is 1 employee (s) with a salary between 700
and 900 Please enter the salary : 3000 PL/SQL procedure successfully completed. G_MESSAGE There are 3 employee (s) with a salary between
2900 and 3100 Please enter the salary : 6000 PL/SQL procedure successfully completed. G_MESSAGE There are no employee salary between 5900 and 6100
Politica de confidentialitate | Termeni si conditii de utilizare |
Vizualizari: 2188
Importanta:
Termeni si conditii de utilizare | Contact
© SCRIGROUP 2024 . All rights reserved