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

PL/SQL Oracle Discussion :

Pb sur un CURSOR explicite dans une boucle FOR LOOP [11gR2]


Sujet :

PL/SQL Oracle

Vue hybride

Message précédent Message précédent   Message suivant Message suivant
  1. #1
    Membre averti
    Homme Profil pro
    Inscrit en
    Mai 2009
    Messages
    41
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France

    Informations professionnelles :
    Secteur : High Tech - Éditeur de logiciels

    Informations forums :
    Inscription : Mai 2009
    Messages : 41
    Par défaut Pb sur un CURSOR explicite dans une boucle FOR LOOP
    Bonjour,

    J'aurais besoin d'aide sur une procédure que j'essaie de mettre en place :

    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
     
    create or replace procedure DataCompliance_Purge_Histo as
     
    BEGIN
        DECLARE 
            CURSOR id_cust Is
                select * from customer cust where cust.customer_number in (43337,11211114);
            c_limit integer := 1000;
            TYPE id_cust_type IS TABLE OF id_cust%ROWTYPE INDEX BY BINARY_INTEGER;
            id_cust_array id_cust_type;
     
        BEGIN 
     
            EXECUTE IMMEDIATE 'truncate table PURGE_HISTO_DC';
     
            FOR IDS IN id_cust LOOP 
                FETCH id_cust BULK COLLECT INTO id_cust_array LIMIT c_limit;
     
                EXECUTE IMMEDIATE 'INSERT INTO PURGE_HISTO_DC (CUSTOMER_NUMBER,CREATION_DATE,EVENT_CONSENT,EVENT_CONSENT_NB,APPLICATION)
                                       select cust.customer_number, cust.update_date, ''CUSTOMER'',cust.customer_number, ''SCR'' 
                                         from customer cust
                                        where cust.customer_number = :1'
                                        USING IDS.customer_number;
            END LOOP IDS;
        end;
    end;
    Lorsque je lance la procédure, j'obtiens une erreur oracle :

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    ORA-01001: curseur non valide
    ORA-06512: à "SIRIUSLMFR.DATACOMPLIANCE_PURGE_HISTO", ligne 23
    ORA-06512: à ligne 2
    Est-ce que vous pouvez m'aider à diagnostiquer le problème ?

  2. #2
    McM
    McM est déconnecté
    Expert confirmé

    Homme Profil pro
    Développeur Oracle
    Inscrit en
    Juillet 2003
    Messages
    4 580
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France, Bouches du Rhône (Provence Alpes Côte d'Azur)

    Informations professionnelles :
    Activité : Développeur Oracle

    Informations forums :
    Inscription : Juillet 2003
    Messages : 4 580
    Billets dans le blog
    4
    Par défaut
    Bonjour,

    1/ A quoi sert cette ligne : FETCH id_cust BULK COLLECT INTO id_cust_array LIMIT c_limit; ?
    Le bulk Collect c'est pour mettre toutes les lignes dans un tableau en 1 fois (sans boucle)

    2/ Pourquoi un execute immediate ? Le nom de la table n'est pas dynamique.

    3/ Simplifions (mais si ça se trouve tu souhaites faire autre chose)

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    CREATE OR REPLACE PROCEDURE DataCompliance_Purge_Histo IS
    BEGIN 
    	EXECUTE IMMEDIATE 'TRUNCATE TABLE PURGE_HISTO_DC'; -- Attention, ceci fait un commit implicite
      FOR IDS IN (SELECT customer_number, update_date  FROM CUSTOMER WHERE customer_number IN (43337,11211114))
      LOOP 
          INSERT INTO PURGE_HISTO_DC (CUSTOMER_NUMBER,CREATION_DATE,EVENT_CONSENT,EVENT_CONSENT_NB,APPLICATION)
          VALUES( ids.customer_number, ids.update_date, 'CUSTOMER', ids.customer_number, 'SCR');                     
      END LOOP;
      -- COMMIT; ? 
    END;
    Ou sans curseur

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    INSERT INTO PURGE_HISTO_DC (CUSTOMER_NUMBER,CREATION_DATE,EVENT_CONSENT,EVENT_CONSENT_NB,APPLICATION)
    SELECT customer_number, update_date, 'CUSTOMER', customer_number, 'SCR'
    FROM CUSTOMER 
    WHERE customer_number IN (43337,11211114);

  3. #3
    Membre averti
    Homme Profil pro
    Inscrit en
    Mai 2009
    Messages
    41
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France

    Informations professionnelles :
    Secteur : High Tech - Éditeur de logiciels

    Informations forums :
    Inscription : Mai 2009
    Messages : 41
    Par défaut
    Merci pour cette réponse,

    Et voici quelque précision :

    Citation Envoyé par McM Voir le message
    3/ Simplifions (mais si ça se trouve tu souhaites faire autre chose)
    * je dois parcours une table de plusieurs millions d'entrées (customer)
    * je réalise plusieurs insert de différentes table.

    => c'est pour cette raison que j'ai mis un cursor.

    Citation Envoyé par McM Voir le message
    2/ Pourquoi un execute immediate ? Le nom de la table n'est pas dynamique
    Je vais vérifier, mais il me semble que sql developper me remonte une erreur si je n'utilise le execute immed

    Citation Envoyé par McM Voir le message
    1/ A quoi sert cette ligne : FETCH id_cust BULK COLLECT INTO id_cust_array LIMIT c_limit; ?
    Comme je brasse une grosse quantité de lignes, je me dis que cela permettra de gagner en performance.

    J'ai essayé de me baser un un post du site https://www.developpez.net/forums/d9...-fetch-cursor/

  4. #4
    Modérateur
    Avatar de Waldar
    Homme Profil pro
    Sr. Specialist Solutions Architect @Databricks
    Inscrit en
    Septembre 2008
    Messages
    8 454
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 47
    Localisation : France, Val de Marne (Île de France)

    Informations professionnelles :
    Activité : Sr. Specialist Solutions Architect @Databricks
    Secteur : High Tech - Éditeur de logiciels

    Informations forums :
    Inscription : Septembre 2008
    Messages : 8 454
    Par défaut
    Citation Envoyé par Philomelo Voir le message
    * je dois parcours une table de plusieurs millions d'entrées (customer)
    * je réalise plusieurs insert de différentes table.
    Regardez du côté de INSERT ALL avec un seul ordre SQL et une seule lecture de la table customer.
    Plusieurs millions de lignes n'est pas effrayant.

+ Répondre à la discussion
Cette discussion est résolue.

Discussions similaires

  1. Réponses: 9
    Dernier message: 31/03/2014, 13h00
  2. [XL-2007] conditions sur i dans une boucle For
    Par pmp87 dans le forum Macros et VBA Excel
    Réponses: 3
    Dernier message: 14/05/2013, 21h31
  3. function sur un movieclip dans une boucle for
    Par totof49 dans le forum ActionScript 1 & ActionScript 2
    Réponses: 0
    Dernier message: 22/08/2009, 16h28
  4. [batch] incrémentation dans une boucle for
    Par bart64 dans le forum Scripts/Batch
    Réponses: 4
    Dernier message: 08/09/2004, 20h05
  5. Réponses: 3
    Dernier message: 06/07/2004, 10h21

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