web-dev-qa-db-ja.com

SQL Serverでトリガーが呼び出されたものを確認する方法は?

私は3,000近くのテーブルと10,000を超えるストアドプロシージャを持つレガシーSQL Serverアプリケーションに取り組んでいます。

これらのストアドプロシージャの1つは、テーブルから必要なデータを削除することです。どれなのかわかりません。

削除されたすべての行を別のテーブルに記録するトリガーをテーブルに作成しました。 veryトリガーがそれを呼び出したストアドプロシージャの名前もログに記録できると便利です。 SQL Server 2008 R2(v10.50)では、このようなことが可能ですか?

そうでない場合、それが呼び出された理由を特定するのに役立つ他の情報がトリガー内から入手できますか?

3
Alex D

あなたの質問に対する部分的な答えは、DBCC INPUTBUFFERを使用することかもしれませんが、これは必然的にレコードを削除するストアドプロシージャを提供しません。これは、クライアントから呼び出された最初のストアドプロシージャを提供します。

アプリケーションコード呼び出し:

EXEC EntryStoredProc  /* this call is the one that will be identified by DBCC INPUTBUFFER */
...
/* inside EntryStoredProc */
EXEC SecondaryProc
...
/* inside SecondaryProc */
DELETE FROM [MyTable] ...

トリガーにロギングを追加するには、次のようなコードを追加します。

DECLARE @EventInfo varchar(200)
DECLARE @EventSource TABLE (EventType nvarchar(30), Parameters int, EventInfo nvarchar(4000)) 

INSERT INTO @EventSource
EXEC ('dbcc inputbuffer (' + @@spid + ') with no_infomsgs')

SELECT TOP 1 @EventInfo = SUBSTRING(APP_NAME() + '.' + ISNULL(EventInfo, ''), 0, 200) 
FROM @EventSource

INSERT INTO MyLogTable (ID, EventInfo)
SELECT d.ID, @EventInfo
FROM deleted

注:これは明らかにパフォーマンスに影響を与えるため、ライブサーバーに長時間放置しないでください。

3

いくつかのオプション:

オプション1:

最善のオプションは、フィルタリングオプションを有効にしてサーバーside traceを実行することです。

このようにして、取得するデータの量を絞り込むことができます。

オプション2:

バージョン(Enterprise)に応じて、DELETEEXECUTEおよびその他のアクションを追跡できるため、SQL Auditを使用できます。オブジェクトレベルも同様です。したがって、関心のあるテーブルをフィルタリングして、監査を有効にすることができます。隠されたSQL監査は拡張イベントを使用することに注意してください。

オプション3:(これは使用していませんが、msdnからのものです)

SQL Server監査バージョン2を使用しない軽量のSQL Serverプロシージャ監査


別のオプションは this 回答で説明されているようにCONTEXT_INFOを使用することです。レガシーコードを変更しないため、これが役立つかどうかはわかりません。

3
Kin Shah