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

Sybase Discussion :

[Sybase ASE 12.5.3] Gestion d'erreur avec @@error


Sujet :

Sybase

  1. #1
    Membre régulier
    Profil pro
    Inscrit en
    Octobre 2005
    Messages
    79
    Détails du profil
    Informations personnelles :
    Âge : 44
    Localisation : France

    Informations forums :
    Inscription : Octobre 2005
    Messages : 79
    Points : 78
    Points
    78
    Par défaut [Sybase ASE 12.5.3] Gestion d'erreur avec @@error
    Bonjour,

    En premier, il y a les scripts puis mes questions suivent, merci.

    script_01.sql

    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
    41
     
    if object_id('a') is not null
       begin
          drop table a
       end
    go
     
    create table a (
    a int null
    )
    go
     
    insert into a (a) values (1)
    go
     
    -- Début de transaction
     
    begin tran
     
       insert into a (a) values (3)
       -- Génère une erreur car la table n'existe pas
       insert into b (b) values (2)
       select @@error
       if @@error <> 0
          begin
            rollback tran
            print "erreur"
            return
          end
     
    commit tran
    go
     
    select * from a
    go
     
    if object_id('a') is not null
       begin
          drop table a
       end
    go
    script_02.sql

    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
    41
    42
    43
     
    if object_id('a') is not null
       begin
          drop table a
       end
    go
     
    create table a (
    a int null
    )
    go
     
    insert into a (a) values (1)
    go
     
    -- Début de transaction
     
    begin tran
     
       insert into a (a) values (3)
       -- Génère une erreur car la table n'existe pas
       insert into b (b) values (2)
       select @@error
       go
     
       if @@error <> 0
          begin
            rollback tran
            print "erreur"
            return
          end
     
    commit tran
    go
     
    select * from a
    go
     
    if object_id('a') is not null
       begin
          drop table a
       end
    go
    script_03.sql

    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
    41
     
    if object_id('a') is not null
       begin
          drop table a
       end
    go
     
    create table a (
    a int null
    )
    go
     
    insert into a (a) values (1)
    go
     
    -- Début de transaction
     
    begin tran
     
       insert into a (a) values (3)
       -- Génère une erreur car la table n'existe pas
       insert into b (b) values (2)
     
       if @@error <> 0
          begin
            rollback tran
            print "erreur"
            return
          end
     
    commit tran
    go
     
    select * from a
    go
     
    if object_id('a') is not null
       begin
          drop table a
       end
    go

    Lorsque j'exécute ces scripts là avec isql j'obtiens :


    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
     
    (1 row affected)
    Msg 208, Level 16, State 1:
    Server 'MUTUDEV', Line 8:
    b not found. Specify owner.objectname or use sp_help to check whether the object
    exists (sp_help may produce lots of output).
     a           
     ----------- 
               1 
     
    (1 row affected)
    Je constate qu'on sort du premier batch juste après "insert into b (b) values (2)".

    Puis on reprend au deuxième batch.

    Faut il en conclure que pour ce type d'erreur la gestion d'erreur n'y fait rien ?
    Pourquoi ?

    Maintenant la même opération avec sqladv :

    script_01.sql

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
     
    (1 row affected)
    Server Message:  Number  208, Severity  16
    Server 'MUTUDEV', Line 7:
    b not found. Specify owner.objectname or use sp_help to check whether the object exists (sp_help may produce lots of output). 
    (1 row affected)
     
    Resultset :
     
    a           
    ----------- 
              1
    script_02.sql

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
     
    (1 row affected)
    Server Message:  Number  208, Severity  16
    Server 'MUTUDEV', Line 7:
    b not found. Specify owner.objectname or use sp_help to check whether the object exists (sp_help may produce lots of output). 
    erreur
    (1 row affected)
     
    Resultset :
     
    a           
    ----------- 
              1
    script_03.sql

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
     
    (1 row affected)
    Server Message:  Number  208, Severity  16
    Server 'MUTUDEV', Line 7:
    b not found. Specify owner.objectname or use sp_help to check whether the object exists (sp_help may produce lots of output). 
    (1 row affected)
     
    Resultset :
     
    a           
    ----------- 
              1
    Je remarque que la gestion d'erreur marche car il a bien fait le print "erreur".

    Pourquoi la gestion d'erreur fonctionne sur le script_02.sql ?


    Je tiens à préciser que le discours tenu par les formateurs sybase concernant la gestion d'erreurs est le suivant :

    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
     
    /*
    Gestion d'erreur lors de mises à jour
    */
     
    if conditions
       begin
     
          declare @err int, @rows int
     
          begin tran
     
          print "#@# Mise à jour de la table ..., champ ..."
     
          -- Instruction DML
     
          select @err = @@error, @rows = @@rowcount
     
          if @err <> 0
             begin
                rollback tran
                raiserror 30001, "table_name", "base_name"
                return
             end
     
          commit tran
     
          print "Nombre de mises à jour : %1!." , @rows
     
       end
    else
       begin
          print "Pas de mise à jour dans la table ..."
       end
    go
    Comment être sûr de sa gestion d'erreurs ?

    Pour information :

    1> select @@version
    2> go
    -----------------------------------------------------------------------------------------------------------------------
    ------------------------------------------------------------------------------------------------------------------------
    ----------------
    Adaptive Server Enterprise/12.5.3/EBF 13197 ESD#6/P/Sun_svr4/OS 5.8/ase1253/1945/64-bit/FBO/Fri Jan 20 09:46:56 2006

  2. #2
    Membre chevronné

    Profil pro
    Inscrit en
    Janvier 2006
    Messages
    1 307
    Détails du profil
    Informations personnelles :
    Âge : 65
    Localisation : Suisse

    Informations forums :
    Inscription : Janvier 2006
    Messages : 1 307
    Points : 1 828
    Points
    1 828
    Par défaut
    Pour le premier script le comportement est normal.

    Dans isql chaque batch est indépendant, et une erreur dans un batch n'affecte pas l'exécution des batchs suivants. De plus, une erreur de ce type (object does not exist) est flaguée au moment de la compilation et non pas au moment de l'exécution. Cela est la raison pour laquelle ce genre de code ne marche pas:

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
     
    if object_id('foo')
        begin
            select ... from foo
        end
    else
        print "La table foo n'existe pas"
    On aura la même erreur (table foo does not exist) même si on se dit que le select ne devrait pas être exécuté en raison de la clause IF.

    Michael

  3. #3
    Membre régulier
    Profil pro
    Inscrit en
    Octobre 2005
    Messages
    79
    Détails du profil
    Informations personnelles :
    Âge : 44
    Localisation : France

    Informations forums :
    Inscription : Octobre 2005
    Messages : 79
    Points : 78
    Points
    78
    Par défaut
    Citation Envoyé par mpeppler

    Pour le premier script le comportement est normal.
    Dans isql chaque batch est indépendant, et une erreur dans un batch n'affecte pas l'exécution des batchs suivants. De plus, une erreur de ce type (object does not exist) est flaguée au moment de la compilation et non pas au moment de l'exécution. Cela est la raison pour laquelle ce genre de code ne marche pas:

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
     
    if object_id('foo')
        begin
            select ... from foo
        end
    else
        print "La table foo n'existe pas"
    On aura la même erreur (table foo does not exist) même si on se dit que le select ne devrait pas être exécuté en raison de la clause IF.

    Michael
    Merci.

    En fait, si je comprends bien, le moteur compile puis exécute, normal !

    Donc dans mon cas, la compilation ne marche pas, il écrit l'erreur, mais n'affecte pas au sein même du batch @@error puis passe au batch suivant.

    D'ailleurs on le voit bien si on exécute ces deux batch :

    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
     
    if object_id('a') is not null
       begin
          drop table a
       end
     
    create table a (
    a int null
    )
     
    insert into a (a) values (1)
     
    -- Début de transaction
     
    begin tran
     
       insert into a (a) values (3)
       -- Génère une erreur car la table n'existe pas
       insert into b (b) values (2)
     
       if @@error <> 0
          begin
            rollback tran
            print "erreur"
            return
          end
     
    commit tran
    go
     
    select @@error
    go
    Le resultset :

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
     
     
    Msg 208, Level 16, State 1:
    Server 'ILLEGAL', Line 17:
    b not found. Specify owner.objectname or use sp_help to check whether the object exists (sp_help may produce lots of output).
     
     ----------- 
             208 
     
    (1 row affected)
    Pour quel genre d'erreur le code ci-dessous va gérer correctement l'erreur ?

    Puisque pour les erreurs de syntaxe, d'objets non trouvé cela ne marche pas.

    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
     
     
    /*
    Gestion d'erreur lors de mises à jour
    */
     
    declare @err int, @rows int
     
    begin tran
     
       print "#@# Mise à jour de la table ..., champ ..."
     
       -- Instruction DML
     
       select @err = @@error, @rows = @@rowcount
     
       if @err <> 0
          begin
             rollback tran
             raiserror 30001, "table_name", "base_name"
             return
          end
     
    commit tran
    print "Nombre de mises à jour : %1!." , @rows
    go
    Les erreurs de compilation, je comprends mais alors quelles erreurs peuvent passer à la compilation et planter à l'exécution ?

    PS :
    Le code de gestion d'erreurs est inspiré (voir plagié) de la documentation (édition 2002) fournie lors de la formation Transact SQL ASE 12.5, chapitre 15-38.

  4. #4
    Membre régulier
    Profil pro
    Inscrit en
    Octobre 2005
    Messages
    79
    Détails du profil
    Informations personnelles :
    Âge : 44
    Localisation : France

    Informations forums :
    Inscription : Octobre 2005
    Messages : 79
    Points : 78
    Points
    78
    Par défaut
    Pas de réponses ?

  5. #5
    Membre chevronné

    Profil pro
    Inscrit en
    Janvier 2006
    Messages
    1 307
    Détails du profil
    Informations personnelles :
    Âge : 65
    Localisation : Suisse

    Informations forums :
    Inscription : Janvier 2006
    Messages : 1 307
    Points : 1 828
    Points
    1 828
    Par défaut
    Toutes les erreurs autres que des erreurs lors de la compilation - cad erreur de droits d'accès, de violation de clé primaire, etc, etc, etc...

    Dans le cas d'une proc. stockée il pourrait aussi y avoir le problème où une table existe au moment où la proc est créée, mais où elle a été droppée entre temps.

    Michael

  6. #6
    Membre régulier
    Profil pro
    Inscrit en
    Octobre 2005
    Messages
    79
    Détails du profil
    Informations personnelles :
    Âge : 44
    Localisation : France

    Informations forums :
    Inscription : Octobre 2005
    Messages : 79
    Points : 78
    Points
    78
    Par défaut
    Merci !

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

Discussions similaires

  1. [SYBASE ASE 12.5.3]Message d'erreur réutilisable
    Par lsone dans le forum Sybase
    Réponses: 8
    Dernier message: 11/01/2007, 23h22
  2. Gestion d'erreur avec ShellExecute
    Par mdriesbach dans le forum VB 6 et antérieur
    Réponses: 2
    Dernier message: 22/09/2006, 09h09
  3. [J2EE/JSP] Gestion des erreurs avec une base SQL server 2005
    Par critok dans le forum Servlets/JSP
    Réponses: 3
    Dernier message: 30/04/2006, 16h57
  4. Gestion des erreurs avec setjump/longjump
    Par gege2061 dans le forum C
    Réponses: 1
    Dernier message: 05/02/2006, 15h51
  5. [Upload] Problème pour gestion d'erreur avec class
    Par allserv dans le forum Langage
    Réponses: 2
    Dernier message: 27/12/2005, 13h00

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