[ORACLE] Erreur à l'insertion

Erreur à l'insertion [ORACLE] - SQL/NoSQL - Programmation

Marsh Posté le 22-03-2004 à 11:36:20    

Bonjour, j'ai compilé un trigger "BEFORE INSERT" sans erreur de compilation :  
 

Code :
  1. CREATE OR REPLACE TRIGGER T_ECICountries 
  2.   BEFORE INSERT ON ECICountries 
  3.   FOR EACH ROW 
  4.  
  5.      DECLARE NbRows INTEGER;
  6.        
  7.       -- Affectation de la numérotation automatique pour l'identifiant du pays 
  8.       BEGIN 
  9.         SELECT S_ECICountries.NEXTVAL INTO :new.ECICountries_Id FROM DUAL; 
  10.        
  11.       -- Si valeur manquante de pays
  12.       IF (:new.ECICountries_ShortName='') OR (:new.ECICountries_ShortName=NULL) THEN
  13.           -- On insère l'info dans table des logs 
  14.           INSERT INTO LogTable VALUES (SYSDATE, 'Valeur manquante ECICountries_ShortName : ','Valeur manquante','ECICountries',:new.ECICountries_Id, Null, 'Warning'); 
  15.           -- Puis on insère 'NR' comme ShortName de pays
  16.           :NEW.ECICountries_ShortName:='NR';
  17.       END IF; 
  18.        
  19.       -- Si nouvelle valeur de pays
  20.       SELECT COUNT(*) INTO NbRows FROM ECICountries WHERE ECICountries_ShortName=:new.ECICountries_ShortName;
  21.       IF NbRows=0 THEN
  22.         -- On insère l'info dans table des logs
  23.         INSERT INTO LogTable VALUES (SYSDATE, 'Nouvelle valeur ECICountries_ShortName : '|| :new.ECICountries_ShortName,'Nouvelle valeur','ECICountries',:new.ECICountries_Id, Null,'Warning'); 
  24.       END IF;
  25.      END;


Je peux insérer "à la main" une ligne dans la table concernée par ce trigger, sans erreur :  
 

Code :
  1. INSERT INTO ECICountries (ECICountries_ShortName, ECICountries_Name) VALUES (FRA, 'FRANCE');


En revanche quand j'éxécute le code suivant :  
 

Code :
  1. INSERT INTO ECICountries (ECICountries_ShortName, ECICountries_Name) 
  2.    SELECT DISTINCT T1.ECICOUNTRIES_NAME, T1.ECICOUNTRIES_NAME 
  3.    FROM ImportTable T1
  4.    WHERE NOT EXISTS (SELECT * FROM ECICountries T2 WHERE T1.ECICOUNTRIES_NAME = T2.ECICountries_ShortName);


J'obtiens l'erreur suivante :  
 

Citation :

ERROR at line 1:  
ORA-04091: table A013009.ECICOUNTRIES is mutating, trigger/function may not see it  
ORA-06512: at "A013009.T_ECICOUNTRIES", line 16  
ORA-04088: error during execution of trigger 'A013009.T_ECICOUNTRIES'


Savez-vous ce que signifie exactement que la tables "is mutating" ?
Merci.

Reply

Marsh Posté le 22-03-2004 à 11:36:20   

Reply

Marsh Posté le 22-03-2004 à 13:51:57    

Cela signifi que la table ECICOUNTRIES est en cours de modification, donc quand tu fais le SELECT dans ton INSERT il refuse de le faire car les données retourné ne seront pas forcement a jour.

Reply

Marsh Posté le 22-03-2004 à 13:55:06    

Merci Thecoin.
Je vais essayer de mettre un commit dans le trigger pour vois si ça va mieux.
 :)

Reply

Marsh Posté le 22-03-2004 à 13:59:12    

Essayes toujours, mais je crois que le COMMIT est implicite dans un tigger.

Reply

Marsh Posté le 22-03-2004 à 14:09:05    

Ca fait pareil avec des commit dans le trigger.
 :(  

Reply

Marsh Posté le 22-03-2004 à 14:11:30    

ludolitaliano a écrit :

Ca fait pareil avec des commit dans le trigger.
 :(  
 


Tu as pas le choix, il va faloir trouver une autre solution
 
Edit: tu voulais faire quoi exactement?


Message édité par thecoin le 22-03-2004 à 14:12:42
Reply

Marsh Posté le 22-03-2004 à 14:15:15    

J'ai mon trigger avant insertion qui gère l'identifiant et qui écrit dans une table de log s'il y a des nouveautés ou des valeurs manquantes.
Voilà sinon j'insère à chaque import des valeurs que je reçois par mail.

Reply

Marsh Posté le 22-03-2004 à 14:17:13    

Tu la vide après chaque utilisation ta table ImportTable?

Reply

Marsh Posté le 22-03-2004 à 14:20:00    

Oui. En fait je la vide avant chaque nouvelle utilisation.

Reply

Marsh Posté le 22-03-2004 à 14:26:35    

Commence alors par faire un DELETE dans ta table ImportTable des enregistrement que tu as déjà dans ECICountries, puis ensuite fait l'INSERT dans ECICountries avec toute les données qu'il te reste dans ImportTable.

Reply

Marsh Posté le 22-03-2004 à 14:26:35   

Reply

Marsh Posté le 22-03-2004 à 14:28:01    

Mais je vais perdre les données déjà dans ECICountries.

Reply

Marsh Posté le 22-03-2004 à 14:29:10    

Bon je l'ai fait pour le test, ça me dit toujours la même chose. Même avec un commit après le delete.

Reply

Marsh Posté le 22-03-2004 à 15:03:51    

Si j'enlève cette partie de code du trigger ça marche :
 
 

Code :
  1. SELECT COUNT(*) INTO NbRows FROM ECIBonds WHERE Description=:new.Description;
  2.       IF NbRows<1 THEN
  3.         -- On insère l'info dans table des logs
  4.         INSERT INTO LogTable VALUES (SYSDATE, 'Nouvelle valeur Description : '|| :new.Description,'Nouvelle valeur','ECIBonds',:new.ECIBonds_Id, Null,'Warning'); 
  5.       END IF;

Reply

Sujets relatifs:

Leave a Replay

Make sure you enter the(*)required information where indicate.HTML code is not allowed