Le traitement de l’anomalie doit être déclenché en passant dans la
partie \code{EXCEPTION} par \code{RAISE}.
\begin{verbatim}
DECLARE
...
nom_erreur EXCEPTION;
...
BEGIN
...
IF anomalie
THEN RAISE nom_erreur;
...
EXCEPTION
WHEN nom_erreur THEN
traitement à effectuer en cas d’anomalie;
END;
\end{verbatim}
Sortie du bloc après exécution du traitement.
\begin{exemple}
Accèder au stock d’un produit de Numéro donné avec Erreur Oracle quand
le produit n’existe pas et Erreur utilisateur quand le stock est
nul. Les anomalies sont placées dans une table \code{terreur(z1
varchar2(30), z2 varchar2(30))}
\begin{verbatim}
DECLARE
...
stock_nul EXCEPTION;
dstock number;
...
BEGIN
SELECT stock INTO dstock FROM tproduit WHERE noproduit = ‘&vnoproduit’;
IF stock = 0
THEN RAISE stock_nul;
traitement quand le stock n’est pas nul...
EXCEPTION
WHEN NO_DATA_FOUND THEN
INSERT INTO terreur VALUES (‘&vnoproduit’, ‘produit inconnu’);
WHEN stock_nul THEN
INSERT INTO terreur VALUES (‘&vnoproduit’, ‘stock nul’);
END;
\end{verbatim}
\end{exemple}
Modifiez le programme en remplaçant une des deux exceptions par \code{OTHERS}.
\begin{exercice} Pour remplacer l’erreur Oracle par une erreur utilisateur, compter le nombre de produits ayant le numéro donné et déclencher une exception si ce nombre est nul.
\end{exercice}
\end{exercice}
\section{Les curseurs}\label{sec:curseur}
\section{Les curseurs}\label{sec:curseur}
\subsection{\code{DECLARE, OPEN, FETCH, CLOSE}}
Lorsqu’une requête \code{SELECT} est susceptible de délivrer plusieurs
Lorsqu’une requête \code{SELECT} est susceptible de délivrer plusieurs
lignes, on associe à celle ci un «curseur explicite» qui va
lignes, on associe à celle ci un «curseur explicite» qui va permettre
permettre d’accéder aux lignes du résultat. L’algorithme est analogue
d’accéder aux lignes du résultat. L’algorithme est analogue au
au traitement d’un fichier séquentiel.
traitement d’un fichier séquentiel.
\subsection{\code{DECLARE, OPEN, FETCH, CLOSE}}
Il faut d'abord d\'eclarer le curseur dans le bloc \code{DECLARE},
ensuite ouvrir le curseur avec la commande \code{OPEN} et penser \`a
le ferm\'e une fois celui-ci utilis\'e. Pour acc\'eter aux donn\'ees
les unes apr\`es les autres il faut utiliser la commande \code{FETCH}.
\begin{exemple} Traitement des rayons d’un étage donné.
\begin{exemple} Traitement des rayons d’un étage donné.
@ -1057,21 +1129,21 @@ END;
\end{verbatim}
\end{verbatim}
\end{exemple}
\end{exemple}
\begin{exercice}Pourcentage de produits ayant un stock nul (une solution avec curseur et une sans).
\begin{exercice}Caculer le pourcentage de produits ayant un stock nul. Proposer une solution avec curseur et une sans.
\end{exercice}
\end{exercice}
\begin{exercice} Créer une table des produits classés par valeur du stock: No de produit, désignation, valeur du stock, classement.
\begin{exercice} Créer une table des produits classés par valeur du stock: No de produit, désignation, valeur du stock, classement.
\end{exercice}
\end{exercice}
\begin{exercice} Créer une table des produits qui n’ont pas de fournisseur et une table des produits qui en ont avec les noms de leurs fournisseurs.
\begin{exercice} Créer une table des produits qui n’ont pas de fournisseur et une table des produits qui en ont avec les noms de leurs fournisseurs.
\end{exercice}
\end{exercice}
\subsection{\code{UPDATE, DELETE ... WHERE CURRENT OF curseur}}
\subsection{\code{UPDATE, DELETE ... WHERE CURRENT OF curseur}}
Lors du parcours d'une table (ou une vue modifiable) par
Lors du parcours d'une table (ou une vue modifiable) par \code{FETCH}
\code{FETCH} à l’aide d’un curseur, il est possible de demander à mettre à jour
à l’aide d’un curseur, il est possible de demander à mettre à jour ou
ou supprimer la ligne courante par la condition \code{WHERE CURRENT
supprimer la ligne courante par la condition \code{WHERE CURRENT OF}
OF} nom du curseur. Le curseur doit avoir été déclaré \code{FOR
nom du curseur. Le curseur doit avoir été déclaré \code{FOR UPDATE}
UPDATE}
\begin{verbatim}
\begin{verbatim}
CURSOR r IS
CURSOR r IS
@ -1088,61 +1160,10 @@ COMMIT;
entre deux exécutions qui voudraient écrire dans la même table.
entre deux exécutions qui voudraient écrire dans la même table.
\begin{exercice}
\begin{exercice}
augmenter de 10\% les produits de plus de 1000\euro{}, et de 5\% les autres.
\'Ecrire un code \plsql{} qui augmenter de 10\% les produits de plus
\end{exercice}
de 1000\euro{}, et de 5\% les autres.
Erreur utilisateur : \code{EXCEPTION, RAISE}
Le traitement de l’anomalie doit être déclenché en passant dans la
partie \code{EXCEPTION} par \code{RAISE}.
\begin{verbatim}
DECLARE
...
nom_erreur EXCEPTION;
...
BEGIN
...
IF anomalie
THEN RAISE nom_erreur;
...
EXCEPTION
WHEN nom_erreur THEN
traitement à effectuer en cas d’anomalie;
END;
\end{verbatim}
Sortie du bloc après exécution du traitement.
\begin{exemple}
Accèder au stock d’un produit de Numéro donné avec Erreur Oracle quand
le produit n’existe pas et Erreur utilisateur quand le stock est
nul. Les anomalies sont placées dans une table \code{terreur(z1
varchar2(30), z2 varchar2(30))}
\begin{verbatim}
DECLARE
...
stock_nul EXCEPTION;
dstock number;
...
BEGIN
SELECT stock INTO dstock FROM tproduit WHERE noproduit = ‘&vnoproduit’;
IF stock = 0
THEN RAISE stock_nul;
traitement quand le stock n’est pas nul...
EXCEPTION
WHEN NO_DATA_FOUND THEN
INSERT INTO terreur VALUES (‘&vnoproduit’, ‘produit inconnu’);
WHEN stock_nul THEN
INSERT INTO terreur VALUES (‘&vnoproduit’, ‘stock nul’);
END;
\end{verbatim}
\end{exemple}
\begin{exercice} Pour remplacer l’erreur Oracle par une erreur utilisateur, compter le nombre de produits ayant le numéro donné et déclencher une exception si ce nombre est nul.