it-swarm.com.de

Wie lösche ich den PRINT-Puffer in SQL?

Ich habe eine sehr lange laufende gespeicherte Prozedur in SQL Server 2005, die ich zu debuggen versuche, und ich verwende den Befehl "Drucken", um es zu tun. Das Problem ist, dass ich die Nachrichten erst ganz am Ende meines Sprocs von SQL Server zurückerhalte. Ich möchte den Nachrichtenpuffer leeren und diese Nachrichten sofort während der Laufzeit des Sprocs sehen können, und nicht erst ganz am Ende meines Sprocs Ende.

207
Erik Forbes

Verwenden Sie die Funktion RAISERROR :

RAISERROR( 'This message will show up right away...',0,1) WITH NOWAIT

Sie sollten nicht alle Ihre Ausdrucke durch Raubkopien ersetzen. Wenn Sie irgendwo eine Schleife oder einen großen Cursor haben, tun Sie dies einfach ein- oder zweimal pro Iteration oder sogar alle paar Iterationen.

Außerdem: Ich habe zum ersten Mal über RAISERROR unter diesem Link erfahren, den ich jetzt als die endgültige Quelle für die Behandlung von SQL Server-Fehlern betrachte und der auf jeden Fall eine Lektüre wert ist:
http://www.sommarskog.se/error-handling-I.html

294
Joel Coehoorn

Aufbauend auf der Antwort von @JoelCoehoorn lasse ich alle meine PRINT-Anweisungen unverändert und folge ihnen einfach mit der RAISERROR-Anweisung, um den Flush auszulösen.

Beispielsweise:

PRINT 'MyVariableName: ' + @MyVariableName
RAISERROR(N'', 0, 1) WITH NOWAIT

Der Vorteil dieses Ansatzes besteht darin, dass die PRINT-Anweisungen Zeichenfolgen verketten können, während RAISERROR dies nicht kann. (So ​​oder so haben Sie die gleiche Anzahl von Codezeilen, wie Sie eine Variable deklarieren und festlegen müssten, die in RAISERROR verwendet werden soll.).

Wenn Sie wie ich AutoHotKey oder SSMSBoost oder ein gleichwertiges Tool verwenden, können Sie einfach eine Verknüpfung wie "] flush" einrichten, um die RAISERROR-Zeile für Sie einzugeben. Dies spart Zeit, wenn es sich jedes Mal um dieselbe Codezeile handelt, d. H. Sie muss nicht angepasst werden, um bestimmten Text oder eine Variable aufzunehmen.

19
Mike

Ja ... Der erste Parameter der RAISERROR-Funktion benötigt eine NVARCHAR-Variable. Versuchen Sie also Folgendes:

-- Replace PRINT function
DECLARE @strMsg NVARCHAR(100)
SELECT @strMsg = 'Here''s your message...'
RAISERROR (@strMsg, 0, 1) WITH NOWAIT

OR

RAISERROR (n'Here''s your message...', 0, 1) WITH NOWAIT
17
tcbrazil

Eine andere bessere Option ist, nicht von PRINT oder RAISERROR abhängig zu sein und einfach Ihre "print" -Anweisungen in eine ## Temp-Tabelle in TempDB oder eine permanente Tabelle in Ihrer Datenbank zu laden, wodurch Sie über eine SELECT-Anweisung aus einem anderen Fenster sofort auf die Daten zugreifen können . Das funktioniert am besten für mich. Die Verwendung einer permanenten Tabelle dient dann auch als Protokoll für die Ereignisse in der Vergangenheit. Die print-Anweisungen sind praktisch für Fehler, aber mithilfe der Protokolltabelle können Sie den genauen Fehlerpunkt auch auf der Grundlage des letzten protokollierten Werts für diese bestimmte Ausführung ermitteln (vorausgesetzt, Sie verfolgen die Gesamtstartzeit der Ausführung in Ihrer Protokolltabelle.)

11
Eric Isaacs

Nur zu Referenzzwecken : Wenn Sie in Skripten (Stapelverarbeitung) und nicht in einer gespeicherten Prozedur arbeiten, wird das Leeren der Ausgabe durch den Befehl GO ausgelöst, z.

print 'test'
print 'test'
go

Im Allgemeinen lautet meine Schlussfolgerung wie folgt: Die Ausgabe von mssql-Skripten, die in SMS GUI oder mit sqlcmd.exe ausgeführt wird, wird bei der ersten GO-Anweisung oder bis zum Ende in die Datei, stdoutput, gui window geschrieben des Skripts.

Das Leeren innerhalb einer gespeicherten Prozedur funktioniert anders, da Sie GO nicht darin platzieren können.

Referenz: tsql Go-Anweisung

4
Robert Lujo