représentés par un identifiant SQL et un code d'erreur MySQL. Un avertissement, contrairement à une erreur, ne fait pas échouer
l'instruction par défaut, mais en l'interceptant dans une requête stockée avec un gestionnaire, vous pouvez décider du
comportement à adopter suite à cet avertissement.
Vous aurez par exemple un avertissement si vous insérez un DATETIME dans une colonne DATE, puisque la donnée sera
tronquée pour correspondre au type de la colonne (l'heure sera supprimée pour ne garder que la date) : code Mysql 1265,
SQLSTATE '01000'.
Utilisation d'une CONDITION
Avec un numéro d'erreur MySQL et un identifiant d'état SQL, il existe une troisième manière d'identifier les erreurs reconnues par
un gestionnaire : une CONDITION.
Une CONDITION est en fait simplement un nom donné à un numéro d'erreur MySQL ou à un identifiant d'état SQL. Cela vous
permet de travailler avec des erreurs plus claires.
Voici la syntaxe à utiliser pour nommer une erreur. Il s'agit à nouveau d'un DECLARE. Les déclarations de CONDITION doivent
se trouver avant les déclarations de gestionnaires.
Code : SQL
DECLARE nom_erreur CONDITION FOR { SQLSTATE identifiant_SQL |
numero_erreur_MySQL };
Exemple : réécrivons la procédure ajouter_adoption_exit() en nommant l'erreur :
Code : SQL
DROP PROCEDURE ajouter_adoption_exit;
DELIMITER |
CREATE PROCEDURE ajouter_adoption_exit(IN p_client_id INT, IN
p_animal_id INT, IN p_date DATE, IN p_paye TINYINT)
BEGIN
DECLARE v_prix DECIMAL(7,2);
DECLARE violation_contrainte CONDITION FOR SQLSTATE '23000';
-
- On nomme l'erreur dont l'identifiant est 23000
"violation_contrainte"
DECLARE EXIT HANDLER FOR violation_contrainte
-
- Le gestionnaire sert donc à intercepter
BEGIN
-
- les erreurs de type "violation_contrainte"
SELECT 'Une erreur est survenue...';
SELECT 'Arrêt prématuré de la procédure';
END;
SELECT 'Début procédure';
SELECT COALESCE(Race.prix, Espece.prix) INTO v_prix
FROM Animal
INNER JOIN Espece ON Espece.id = Animal.espece_id
LEFT JOIN Race ON Race.id = Animal.race_id
WHERE Animal.id = p_animal_id;
INSERT INTO Adoption (animal_id, client_id, date_reservation,
date_adoption, prix, paye)
VALUES (p_animal_id, p_client_id, CURRENT_DATE(), p_date,
v_prix, p_paye);
SELECT 'Fin procédure';
END|
DELIMITER ;
Partie 5 : Sécuriser et automatiser ses actions
298/414
www.openclassrooms.com
l'instruction par défaut, mais en l'interceptant dans une requête stockée avec un gestionnaire, vous pouvez décider du
comportement à adopter suite à cet avertissement.
Vous aurez par exemple un avertissement si vous insérez un DATETIME dans une colonne DATE, puisque la donnée sera
tronquée pour correspondre au type de la colonne (l'heure sera supprimée pour ne garder que la date) : code Mysql 1265,
SQLSTATE '01000'.
Utilisation d'une CONDITION
Avec un numéro d'erreur MySQL et un identifiant d'état SQL, il existe une troisième manière d'identifier les erreurs reconnues par
un gestionnaire : une CONDITION.
Une CONDITION est en fait simplement un nom donné à un numéro d'erreur MySQL ou à un identifiant d'état SQL. Cela vous
permet de travailler avec des erreurs plus claires.
Voici la syntaxe à utiliser pour nommer une erreur. Il s'agit à nouveau d'un DECLARE. Les déclarations de CONDITION doivent
se trouver avant les déclarations de gestionnaires.
Code : SQL
DECLARE nom_erreur CONDITION FOR { SQLSTATE identifiant_SQL |
numero_erreur_MySQL };
Exemple : réécrivons la procédure ajouter_adoption_exit() en nommant l'erreur :
Code : SQL
DROP PROCEDURE ajouter_adoption_exit;
DELIMITER |
CREATE PROCEDURE ajouter_adoption_exit(IN p_client_id INT, IN
p_animal_id INT, IN p_date DATE, IN p_paye TINYINT)
BEGIN
DECLARE v_prix DECIMAL(7,2);
DECLARE violation_contrainte CONDITION FOR SQLSTATE '23000';
-
- On nomme l'erreur dont l'identifiant est 23000
"violation_contrainte"
DECLARE EXIT HANDLER FOR violation_contrainte
-
- Le gestionnaire sert donc à intercepter
BEGIN
-
- les erreurs de type "violation_contrainte"
SELECT 'Une erreur est survenue...';
SELECT 'Arrêt prématuré de la procédure';
END;
SELECT 'Début procédure';
SELECT COALESCE(Race.prix, Espece.prix) INTO v_prix
FROM Animal
INNER JOIN Espece ON Espece.id = Animal.espece_id
LEFT JOIN Race ON Race.id = Animal.race_id
WHERE Animal.id = p_animal_id;
INSERT INTO Adoption (animal_id, client_id, date_reservation,
date_adoption, prix, paye)
VALUES (p_animal_id, p_client_id, CURRENT_DATE(), p_date,
v_prix, p_paye);
SELECT 'Fin procédure';
END|
DELIMITER ;
Partie 5 : Sécuriser et automatiser ses actions
298/414
www.openclassrooms.com
