web-dev-qa-db-fra.com

Comment enregistrer les détails d'erreur lors de l'utilisation de TRY / Catch pour les commandes de sauvegarde SQL dynamique

Lors de la délivrance d'une commande de sauvegarde dans une procédure stockée qui utilise un essais SQL Catch and Dynamic SQL, les messages d'erreur sont très généraux par rapport à l'exécution directe de la commande de sauvegarde.

Essayez/Catch dans SP:

    begin try
        execute sp_executesql @sql;  -- a backup command
    end try
    begin catch  
        print ERROR_MESSAGE();  -- save to log, etc.
    end catch

Résulte en

50000: USP_Backup: 117: La base de données de sauvegarde se termine anormalement.

weons délivrant la commande brute:

    backup DATABASE someDb to disk...

Résultats dans de meilleurs détails:

Erreur de recherche - Erreur de base de données SQL Server: une erreur d'E/S non recouverte s'est produite sur le fichier "H:\foldername\nom_file.bak:" 112 (Il n'y a pas assez d'espace sur le disque.).

Existe-t-il un moyen d'attraper ces détails dans des variables dans la procédure stockée (pour vous connecter, transmettre à l'appelant, pour la logique de réessaye)? Il semble que les détails suivent sur le canal de message, mais j'aimerais qu'ils soient disponibles dans le SP.

10
crokusek

Eh bien, je sais que c'est un vieux fil, et je sais ce que je suis sur le point de proposer est un piratage compliqué, mais au cas où cela peut aider n'importe qui, voici: puisque ces erreurs de sauvegarde sont connectées, vous pouvez utiliser xp_readerrorlog dans la capture. Bloquer pour gratter le journal pour un message associé (erreur ou infos). Vous pouvez utiliser Google pour xp_readerrorlog params mais en bref, vous pouvez spécifier une chaîne de recherche et un filtre de temps de départ qui sont utiles dans ce cas. Je ne sais pas si cela aiderait votre logique de nouvelle tentative, mais de capturer des informations ou des erreurs pour la journalisation, j'ai proposé quelque chose comme ça ...

IF OBJECT_ID('tempdb.dbo.#Results') IS NOT NULL DROP TABLE #Results
CREATE TABLE #Results (LogDate datetime,ProcessInfo nvarchar(100),LogText nvarchar(4000))
BEGIN TRY
SELECT @begintime = GETDATE()
EXEC sp_executesql @SQL --your backup statement string
INSERT #Results
EXEC  xp_readerrorlog 0, 1, N'backed up',@databasename,@begintime
SELECT @result = LogText from #Results where ProcessInfo = 'Backup' order by logdate desc
END TRY
BEGIN CATCH
INSERT #Results
EXEC  xp_readerrorlog 0, 1, N'Backup',@databasename,@begintime
SELECT @result = LogText from #Results where ProcessInfo = 'spid'+cast(@@SPID as varchar(6)) order by logdate desc
END CATCH
PRINT @result

Ht

2
Andy McD

Vous pouvez enregistrer les détails d'erreur à une table. Vous pouvez également créer un fichier journal, mais cela peut nécessiter une CLR ou XP_CMDSHELL à faire. Vous pouvez également envoyer un courrier de la base de données, mais cela peut provoquer des problèmes de spam et ce n'est pas un journal approprié.

La table est la plus simple.

  1. Créer une table pour stocker les erreurs
  2. Créer une procédure stockée qui insère dans la table d'erreur
  3. Appelez la procédure stockée dans le bloc de capture

Regardez l'exemple de Jeremy Kadlec fourni dans le lien ci-dessous:

http://www.mssqltips.com/sqlservertip/1152/standardisé-sql-server-error-handling-and-Centralized-logging/

0
brian