IdentifiantMot de passe
Loading...
Mot de passe oublié ?Je m'inscris ! (gratuit)
Navigation

Inscrivez-vous gratuitement
pour pouvoir participer, suivre les réponses en temps réel, voter pour les messages, poser vos propres questions et recevoir la newsletter

Oracle Discussion :

Créer une table dans un trigger


Sujet :

Oracle

  1. #1
    Membre actif
    Profil pro
    Inscrit en
    Février 2007
    Messages
    762
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Février 2007
    Messages : 762
    Points : 208
    Points
    208
    Par défaut Créer une table dans un trigger
    bonjour à tous et à toutes,
    Est il possible de créer une table dans un trigger Oracle voiçi le code :
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    23
    24
    25
    26
    27
    28
    29
    30
    31
    32
    33
    34
    35
    36
    37
    38
    39
    40
    CREATE OR REPLACE TRIGGER TAGE_Ins
    before delete on TAGS
    declare 
    wMAT_Doublon varchar2(14);
    wCount number(4);
    wCount1 number(4);
    i number(4);
    begin
      select count(*) into wCount from TAGS;
      if wCount>1 then 
        select count(*)into wCount1 from TAGS where TAGS.AGS_C_MAT_AGENT in(select TAGS.AGS_C_MAT_AGENT from tags group by AGS_C_MAT_AGENT having count(AGS_C_MAT_AGENT)>1);
      end if;
      if wCount1 > 1 then
        i:=1;
        while (i<=wCount1) loop
          if i>1 then
            SELECT max(TAGS2.AGS_C_MAT_AGENT) into wMAT_Doublon 
            FROM TAGS2 where TAGS2.AGS_C_MAT_AGENT in(select TAGS2.AGS_C_MAT_AGENT from tags2 group by AGS_C_MAT_AGENT having count(AGS_C_MAT_AGENT)>1);
          else
            SELECT max(TAGS.AGS_C_MAT_AGENT) into wMAT_Doublon 
            FROM TAGS where TAGS.AGS_C_MAT_AGENT in(select TAGS.AGS_C_MAT_AGENT from tags group by AGS_C_MAT_AGENT having count(AGS_C_MAT_AGENT)>1);
          end if;
          DBMS_OUTPUT.ENABLE( 1000000 ) ; 
          DBMS_OUTPUT.PUT_LINE( ' ' || 'mat doublon ' || wMAT_Doublon) ;
          DBMS_OUTPUT.PUT_LINE( ' ' || 'wCount1 ' || wCount1) ;
          DBMS_OUTPUT.PUT_LINE( ' ' || 'i ' || i) ;
          insert into TAGE (AGE_C_MAT_AGENT,AGE_C_CODE_EH,AGE_C_DATE_PAIE,AGE_C_CODE_LIGNE)select AGS_C_MAT_AGENT,AGS_C_CODE_EH,AGS_C_DATE_PAIE,
          AGS_C_CODE_LIGNE from TAGS where TAGS.AGS_C_MAT_AGENT <> wMAT_Doublon;
          insert into TAGE (AGE_C_MAT_AGENT,AGE_C_CODE_EH,AGE_C_DATE_PAIE,AGE_C_CODE_LIGNE)select distinct AGS_C_MAT_AGENT,AGS_C_CODE_EH,AGS_C_DATE_PAIE,
          AGS_C_CODE_LIGNE from TAGS where TAGS.AGS_C_MAT_AGENT = wMAT_Doublon;
          i:=i+1;
          create table tags2 as
          select * from tags
          minus
          select * from tags where tags.AGS_C_MAT_AGENT = wMAT_Doublon; 
          end loop;
     end if;
      insert into TSTA (STA_AGE_C_MAT_AGENT,STA_L_NB_SECONDE,STA_L_NB_AGENT_SEC) select AGS_C_MAT_AGENT,AGS_L_NB_SECONDE,AGS_L_NB_AGENT_SECONDE from tags;
    end;
    Je ne comprends pas car je l'avais testé hier et maintenant j'ai l'erreur suivante :
    "Error at line 30: PLS-00103: Encountered the symbol "CREATE" when expecting one of the following:

    ( begin case declare end exit for goto if loop mod null
    pragma raise return select update while with "

  2. #2
    Expert éminent sénior Avatar de mnitu
    Homme Profil pro
    Ingénieur développement logiciels
    Inscrit en
    Octobre 2007
    Messages
    5 611
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France, Marne (Champagne Ardenne)

    Informations professionnelles :
    Activité : Ingénieur développement logiciels
    Secteur : High Tech - Éditeur de logiciels

    Informations forums :
    Inscription : Octobre 2007
    Messages : 5 611
    Points : 11 252
    Points
    11 252
    Par défaut
    Les instructions DDL provoque un commit automatique ce qui est interdit dans un trigger. De plus les DDL ne peuvent pas être exécuté que via sql dynamique. La solution sera donc de créer la table via une procédure autonome appelée depuis le trigger. Mais avec Oracle ça c’est la mauvais solution. La bonne solution sera de créer les objets à l’installation de l’application.

  3. #3
    Membre actif
    Profil pro
    Inscrit en
    Février 2007
    Messages
    762
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Février 2007
    Messages : 762
    Points : 208
    Points
    208
    Par défaut réponse à mnitu
    Merci pour votre réponse, j'ai regardé sur le site le cours sur les objets Oracle, d'après ce que j'ai compris il y a 2 sorte d'objets les objets de colonne et les objets de ligne, dans mon cas que me conseilleriez vous? Et si vous pouviez me donnez un peu plus de détails sur votre idée d'objet, ça m'aiderait bien je vous donne le code de la table TAGS sur laquelle j'ai créé le trigger :
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    CREATE TABLE  "TAGS" 
       (	"AGS_C_CODE_EH" CHAR(5), 
    	"AGS_C_CODE_LIGNE" NUMBER(1,0), 
    	"AGS_C_MAT_AGENT" VARCHAR2(14), 
    	"AGS_L_NB_SECONDE" NUMBER(4,0), 
    	"AGS_L_NB_AGENT_SECONDE" NUMBER(7,0), 
    	"AGS_C_DATE_PAIE" CHAR(10)
       ) ;
    Merci à vous

  4. #4
    Expert éminent sénior Avatar de mnitu
    Homme Profil pro
    Ingénieur développement logiciels
    Inscrit en
    Octobre 2007
    Messages
    5 611
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France, Marne (Champagne Ardenne)

    Informations professionnelles :
    Activité : Ingénieur développement logiciels
    Secteur : High Tech - Éditeur de logiciels

    Informations forums :
    Inscription : Octobre 2007
    Messages : 5 611
    Points : 11 252
    Points
    11 252
    Par défaut
    Votre trigger c’est un serpent qui se morde la queue : il veut sélectionner des données à partir d’une table qui n’existe pas. Et si c’est toute à fait possible d’utiliser du SQL dynamique pour réaliser cette désidérata c’es inutile et très coûteux. Essayer de nous expliquer ce que vous essayez d’accomplir.
    Un autre conseil : c’est contre-productif de compter les enregistrements dans une table juste pour décider d’exécuter le traitement sur la table. Il est mieux d’exécuter toujours le traitement qui ne fera rien en cas d’absence des données correspondent aux critères de recherche.

  5. #5
    Membre actif
    Profil pro
    Inscrit en
    Février 2007
    Messages
    762
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Février 2007
    Messages : 762
    Points : 208
    Points
    208
    Par défaut réponse à mnitu
    Bon ok je vais vous expliquer clairement ce que je veux faire : en fait je fais du chargement de données avec SQLLOADER dans la table TAGS; TAGS étant une table temporaire que je vide pour alimenter 2 tables :
    TAGE((PK)AGE_C_MAT_AGENT,AGE_C_CODE_EH,AGE_C_DATE_PAIE,AGE_CODE_LIGNE);
    TSTA((FK)STA_AGE_C_MAT_AGENT,STA_L_NB_SECONDE,STA_L_NB_AGENT_SEC);
    J'ai écrit ce trigger sur la table TAGS car dans le fichier texte que je charge il y a des doublons sur AGE_C_MAT_AGENT clé primaire sur la table TAGE, au départ voiçi le trigger que j'avais écrit qui fonctionne quand dans le fichier chargé il n'y a q'un seul doublon :
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
     
    CREATE OR REPLACE TRIGGER TAGE_Ins
    before delete on TAGS
    declare 
    wMAT_Doublon varchar2(14);
    wCount number(4);
    begin
      select count(*) into wCount from TAGS;
      if wCount>1 then 
        SELECT TAGS.AGS_C_MAT_AGENT into wMAT_Doublon
        FROM TAGS
        GROUP BY AGS_C_MAT_AGENT
        HAVING Count(AGS_C_MAT_AGENT)>1;  
      end if;
      DBMS_OUTPUT.ENABLE( 1000000 ) ; 
      DBMS_OUTPUT.PUT_LINE( ' ' || 'mat doublon' || wMAT_Doublon) ;
      insert into TAGE (AGE_C_MAT_AGENT,AGE_C_CODE_EH,AGE_C_DATE_PAIE,AGE_C_CODE_LIGNE)select AGS_C_MAT_AGENT,AGS_C_CODE_EH,AGS_C_DATE_PAIE,
      AGS_C_CODE_LIGNE from TAGS where TAGS.AGS_C_MAT_AGENT <> wMAT_Doublon;
      insert into TAGE (AGE_C_MAT_AGENT,AGE_C_CODE_EH,AGE_C_DATE_PAIE,AGE_C_CODE_LIGNE)select distinct AGS_C_MAT_AGENT,AGS_C_CODE_EH,AGS_C_DATE_PAIE,
      AGS_C_CODE_LIGNE from TAGS where TAGS.AGS_C_MAT_AGENT = wMAT_Doublon;
      insert into TSTA (STA_AGE_C_MAT_AGENT,STA_L_NB_SECONDE,STA_L_NB_AGENT_SEC) select AGS_C_MAT_AGENT,AGS_L_NB_SECONDE,AGS_L_NB_AGENT_SECONDE from tags;
    end;
    Ce trigger là fonctionne correctement mais je voudrais pouvoir gérer le cas où il y aurait 2 ou plus doublons. et pour l'instant je ne vois pas comment faire pour améliorer mon trigger pour gérer ces éventualités là.
    Voilà j'espère avoir été plus clair.
    Merci à vous

  6. #6
    Expert éminent sénior Avatar de mnitu
    Homme Profil pro
    Ingénieur développement logiciels
    Inscrit en
    Octobre 2007
    Messages
    5 611
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France, Marne (Champagne Ardenne)

    Informations professionnelles :
    Activité : Ingénieur développement logiciels
    Secteur : High Tech - Éditeur de logiciels

    Informations forums :
    Inscription : Octobre 2007
    Messages : 5 611
    Points : 11 252
    Points
    11 252
    Par défaut
    Utilisez select distinct pour éviter les doublons ; ou avec un group by en fonction de vos besoins. Remplacez sqlloader par une table externe.

  7. #7
    Membre actif
    Profil pro
    Inscrit en
    Février 2007
    Messages
    762
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Février 2007
    Messages : 762
    Points : 208
    Points
    208
    Par défaut réponse à mnitu
    Merçi pour votre réponse,
    Oui c'est ce que j'avais déjà fait sur d'autres tables en effet votre solution j'y pensais de toute façon, mais je voulais optimiser mon trigger; pourriez vous me dire si vous savez l'existence de tableau dans un trigger car je ne trouve pas trop d'explications à ce sujet
    Merçi encore

Discussions similaires

  1. Réponses: 53
    Dernier message: 03/08/2007, 14h50
  2. Comment créer une table dans une table ?
    Par Invité dans le forum Débuter
    Réponses: 8
    Dernier message: 15/06/2007, 14h55
  3. Réponses: 1
    Dernier message: 15/05/2007, 12h01
  4. [VB.NET] Comment créer une table dans base de données ?
    Par ptitesouris dans le forum VB.NET
    Réponses: 3
    Dernier message: 03/05/2006, 08h46
  5. Comment créer une Table dans 1 Bdd ACCESS avec Builder??
    Par makandja dans le forum C++Builder
    Réponses: 6
    Dernier message: 17/03/2004, 20h21

Partager

Partager
  • Envoyer la discussion sur Viadeo
  • Envoyer la discussion sur Twitter
  • Envoyer la discussion sur Google
  • Envoyer la discussion sur Facebook
  • Envoyer la discussion sur Digg
  • Envoyer la discussion sur Delicious
  • Envoyer la discussion sur MySpace
  • Envoyer la discussion sur Yahoo