Frage

Ich erstelle einen Auslöser, um zu verfolgen, wie der Prozedurtext war ALTERed.

In einem Datenbank -DDL -Auslöser können Sie über den aktuellen Prozedurtext übertragen /EVENT_INSTANCE/TSQLCommand.

Auch nach Untersuchung EVENTDATA(), Es enthielt keine Werte für die vorherige Definition des Verfahrens zuvor ALTER.

Gibt es eine Möglichkeit, früheren Text abzurufen, wie es möglich ist, gelöschte Werte in DML -Triggern mithilfe zuzugreifen DELETED Tisch?

create trigger trgDDLAuditQuery
on  database
for     alter_procedure
as 
begin
    set nocount on;

    declare @data xml
    set @data = EVENTDATA()

    insert  dbo.tblQueryAudit(ObjectName, TSQLCommand)
    select  @data.value('(/EVENT_INSTANCE/ObjectName)[1]', 'nvarchar(256)'), 
        --; Only gets currently changed procedure text, not previous one
        @data.value('(/EVENT_INSTANCE/TSQLCommand)[1]', 'nvarchar(max)')
end
GO
War es hilfreich?

Lösung

Der Auslöser läuft nach der Änderung, soweit ich das erkennen kann, dass kein Zugriff auf die "Bevor" -Werte besteht. Die EventData () ist definiert und es gibt keine Bestimmung für "vorher". Infolgedessen müssen Sie den aktuellen Wert im Protokoll nur aufzeichnen. Wenn Sie jedoch Ihr Protokoll mit diesem Befehl vorpopulieren:

    INSERT INTO dbo.tblQueryAudit
            (ObjectName, TSQLCommand)
    SELECT
        o.Name,m.definition
        FROM sys.objects                 o
            INNER JOIN sys.sql_modules   m ON o.object_id=m.object_id
        WHERE type='P'

Sie können Ihren Auslöser verwenden und dennoch ein vollständiges Bild von allen Änderungen haben. Ihr Protokoll würde alle vorherigen Versionen sowie die aktuelle Version jedes Prozedur haben. Sie können meine Version des Triggers verwenden (siehe unten), wo Sie Zugriff auf einige der anderen Spalten von sys.objects und sysql_modules haben, wie:

uses_ansi_nulls
uses_quoted_identifier
is_schema_bound
null_on_null_input
principal_id

das könnte auch praktisch für Protokollierung sein. Alternative Version:

CREATE trigger trgDDLAuditQuery
on  database
for             alter_procedure
as 
begin
    set nocount on;

    DECLARE @EventData      xml
    SET @EventData=EVENTDATA()

    INSERT INTO dbo.tblQueryAudit
            (ObjectName, TSQLCommand) --hope you have  datetime column that defaults to GETDATE()
        SELECT
            o.Name,m.definition
            FROM sys.objects                 o
                INNER JOIN sys.sql_modules   m ON o.object_id=m.object_id
            WHERE o.Name=@EventData.value('(/EVENT_INSTANCE/ObjectName)[1]', 'nvarchar(max)')
                --modify as necessary AND type='P'

end
GO
Lizenziert unter: CC-BY-SA mit Zuschreibung
Nicht verbunden mit StackOverflow
scroll top