2 votes

SQL Server SET XACT_ABORT ON et JAVA

J'ai une procédure stockée qui fonctionne comme prévu. L'extrait est présenté ci-dessous :

BEGIN
SET XACT_ABORT ON;
BEGIN TRANSACTION;  

INSERT Table1...;
INSERT Table2...;

COMMIT TRANSACTION; 
END

Si une erreur se produit dans Table2, l'insertion de Table1 est annulée. Le problème vient de l'appel Java à la procédure stockée. Le code ci-dessous ne lèvera pas d'exception si XACT_ABORT est activé ;

    psmt = conn.prepareStatement(query);
    psmt.setInt(1, id);
    psmt.execute();
    psmt.close();

Lorsque j'exécute une procédure stockée dans SQL Server Management Studio, je constate que deux messages sont renvoyés. L'un de succès, l'autre d'erreur : bien que les insertions soient annulées.

(1 row(s) affected)
Msg 515, Level 16, State 2...

Que faut-il, dans l'appel Java, pour que l'exception/erreur soit reconnue ? ...Pour lire tous les messages ?

0voto

Andomar Points 115404

Essayez d'ajouter :

set nocount on;

au début de la procédure ?

0voto

Eli Points 1651

Je me suis battu avec XACT_ABORT dans un passé pas si lointain et votre question m'a fait faire un voyage dans le passé. Mes problèmes étaient similaires aux vôtres et il semble que ma solution fonctionnera très bien dans votre cas également.
XACT_ABORT annulera toutes les transactions, vous laissant dans l'état dans lequel vous étiez avant l'exécution de votre code. Cela signifie que tous les enregistrements de la requête problématique, y compris le message d'erreur, disparaîtront avec le vent ; il y a cependant un endroit qui est "protégé" de ce retour en arrière, et c'est une variable. Vous pouvez en tirer parti, comme je vais vous le montrer ci-dessous.

Voici la structure du code que j'ai utilisé :

BEGIN
    SET XACT_ABORT ON;
    BEGIN TRANSACTION;  
    DECLARE @MSG VARCHAR(MAX);

    BEGIN TRY
        INSERT Table1...;
    END TRY
    BEGIN CATCH
        SET @MSG = 'Table1: ' + ERROR_MESSAGE();
        GOTO failure; /* SEGMENT BELOW WHICH WOULD TAKE CARE OF YOUR ERROR MESSAGES*/
    END CATCH
    /* REPEAT ABOVE SEGMENT FOR ALL INSERTS*/

    GOTO SUCCESS; /* THIS IS HERE SO THAT YOU CAN SKIP THE FAILURE SEGMENT IN THE EVENT THAT ALL WENT WELL UP UNTIL HERE*/

    FAILURE:
        ROLLBACK; 
        RETURN @MSG;

    SUCCESS:
        COMMIT TRANSACTION; 
END

Prograide.com

Prograide est une communauté de développeurs qui cherche à élargir la connaissance de la programmation au-delà de l'anglais.
Pour cela nous avons les plus grands doutes résolus en français et vous pouvez aussi poser vos propres questions ou résoudre celles des autres.

Powered by:

X