2009-06-13 6 views
9

私は、エラーが発生したときや開発中ではなく、実稼働環境で実行されるログ/監査コードをいくつか書いています。 Coding Horror's experiences with dead-locking and loggingを読んだ後、私はアドバイスを求めるべきだと決めました。 (私のために動作しません「ログインしていない」のジェフのソリューションは、これが法的に義務付けられたセキュリティ監査である)MS SQL Serverの追加専用テーブルのロックを最小限に抑えるためのアドバイスはありますか?

は競合とデッドロックを最小にするのに適した分離レベルはありますか?挿入ステートメントまたはストアドプロシージャに追加できるクエリヒント

私は、監査テーブル以外のすべてのトランザクションの整合性について深く気に。考えられるのは、エントリーがいくつか失敗した場合に問題になることはないということです。ロギングが他のトランザクションを停止すると、それは悪いことになります。

私は何とか結果を表示できるようにする必要があるため、ファイルへのロギングはあまり魅力的であるが、私は、データベースまたはファイルにログを記録することができます。ファイルへのロギングは、ロギングが他のコードに干渉しないことを(ほぼ)保証します。

+0

どのバージョンのSQL Serverですか? –

+0

SQL 2000では、オフィスはいつかSQL 2008にジャンプするという噂があります。 – MatthewMartin

答えて

5

通常のトランザクション(すなわち。COMMITTED READ)すでに「最小限」のロックを行い挿入します。インサートが他の操作とどのように混ざっているかに関わらず、インサートの集中的なアプリケーションはインサートのデッドロックにはなりません。最悪の場合、集中的な挿入システムは、挿入が発生するホット・スポットでページ・ラッチ競合を引き起こす可能性がありますが、デッドロックは発生しません。

  • システムは、(彼らはそれがその後、来て、よくそれに値するしていた高い分離レベルを使用している次のいずれかのように、遊びによりが存在しなければならないジェフによって記載されているように、デッドロックを引き起こすことが

  • 彼らがそうもはや「を追加専用」)
  • デッドロックチェーンは、アプリケーション層のロックを関与
  • (すなわち。ネットlog4netのフレームワークでlock文)は検出不能が生じている(トランザクション中にログテーブルからの読み取りなかったですデッドロック(つまり、アプリケーションがハングする)。問題を解決するにはプロセス・ダンプを見ることが必要なので、これは彼らが持っていたシナリオだと思います。

READ COMMITTED分離レベルのトランザクションでのみログインすると、安全です。あなたが別のトランザクションや別の接続にログオンしたとしても、問題がまだ現れる可能性があるので、私はそうだと思っています(つまり、アプリケーション層のロックを含むデッドロック)。

+1

"READ COMMITTED分離レベルのトランザクションでのみログインするだけで安全です。"本当じゃない。大きなトランザクションに参加している場合は、ロギングテーブルを埋め込むときにトランザクション全体をブロックすることができます(ロッキングテーブルがブロックされていると、何らかのクレイジーなレポートが実行されているためです)。また、これはデッドロックの中心にあなたを開きます! –

+2

いいえ、単に真実ではありません。 INSERTは、トランザクション内で何をしていても、(コミットされた)レポートの後ろでブロックしません。また、同時INSERTはデッドロック・チェーンには現れません。なぜなら、相互に背後でもSELECTの後ろでもブロックしないからです。挿入をブロックすることができるものは、挿入ポイント(すなわち直列化可能なレポート)、テーブルのSロック(すなわち反復可能なレポートからのエスカレーション)またはXロック(つまりいくつかのアクティビティ*その他*テーブルXのロックにエスカレートした更新のように、「追加のみ」よりも)。 –

+2

コミットされた読込みでテーブルに(クラスタ化インデックスを使用して)INSERTすると、ページのIXロックが取得され、キーのXロックが取得されます。ページ上のIXロックを取得できない場合は待機し、取得できない場合はキーをXロックして待機します。 SELECT文には共有ロックが必要です。ロックは競合する可能性があります。デッドロックが存在する可能性があります。 Read:http://msdn.microsoft.com/en-us/library/ms186396.aspx –

1

あなたは、監査テーブルのトランザクションの整合性を気にしないので、あなたは明らかにトランザクション(すなわち、それが完了した後)の外側をロギング実行することができます。これにより、取引への影響が最小限に抑えられます。あなたがロックを最小限に抑えたい場合は

また、あなたは可能な限りあなたのクエリワークロードのほどは、非クラスタ化インデックスをカバーしていることを確認してみてください。 (SQL Server 2005以降では、NCインデックスのINCLUDEステートメントを使用すると大きな違いが生じる可能性があります)

+0

注:トランザクションが完了した後にすべてのログを実行すると、長時間実行されているトランザクションまたは中断されたトランザクションをデバッグすることはかなり困難になります。 –

+0

ポスターは、トランザクションが完了している限り、ロギングが失敗したかどうかは問題ではないことを既に明確にしています。トランザクションは可能な限り短くする必要があります。 –

+0

私はこの文脈で(すなわち別のスレッドで)これはおそらく(つまり、完了した後)よりもおそらく良いです(つまり、完了した後) –

1

「通常の」データベースとのロックに関する問題を回避する簡単な方法の1つは、同じデータベース。あなたのログ用に別のデータベースを作成するだけです。ボーナスとして、ロギングデータベースが急速に成長しても、メインDBに断片化が発生することはありません。 Personall、私は通常ファイルにログすることを好む - しかし、私はエディターであるVIMで重いテキスト操作をするのに慣れています。別のDBにログを記録すると、デッドロックの問題を回避できます。

あなたが使用しているロギングフレームワーク用に独自のデータベースアペンダーを作成しようとすると、あなたのロックについて非常に注意してください(私が推測しているのは、あなたが参照しているブログ記事のJeffをトリップしたものです)。正しく書かれている(Jeffの記事のいくつかのコメントを参照)、何かを行わない限り、ロギングフレームワークにロックの問題はないはずです奇数

+0

私はロギングテーブルのためのまったく新しいデータベースを導入するとかなり積極的だと思う、とにかく必要に応じてファイルグループを使用して各テーブルのまた、トランザクションを分散配置している場合、別のDBにログを記録すると、その操作が分散トランザクションに参加している場合、実際には悪化する可能性があります。 –

+0

分散トランザクションを使用している場合、私はあなたのログを登録する*ではない*とアドバイスします。何かがトランザクションのロールバックを引き起こし、何が壊れたのログを持っていないようなものはありません... –

5

ログテーブルの一貫性を気にしない場合、すべてのログをの別のスレッドから実行しないでください。

長時間実行しているトランザクションの診断では、ログが重要な役割を果たす可能性があるため、トランザクションが完了するのを待つことはほとんどありません。また、ロールバックしたトランザクションをすべて見ることができます。

新しいロギングメッセージがある場合は、スタックトレースとすべてのロギングデータをロギングスレッドのchuck it on a queueに取得し、1回のトランザクションでそれらをdbにフラッシュします。ロックを最小限に

ステップ:

  • (KEY)はすべてメインスレッド/接続/トランザクションの外部でログテーブルに追加行います。
  • ログメッセージを追加するたびにログテーブルに単調増加するクラスターインデックス(例:int identity)が増加していることを確認します。これにより、挿入されるページは通常メモリ内にあり、ヒープテーブルで得られるパフォーマンスのヒットを避けることができます。
  • トランザクションのログに複数の追加を実行します(トランザクション内の10個の挿入がトランザクションから10個以上挿入され、通常はより少ないロックを取得または解放します)。
  • Nミリ秒ごとにあなたのデータベースにログを記録するだけです。作品のバッチアップ。
  • 履歴を報告する必要がある場合は、ロギングテーブルのパーティション分割を検討することができます。例:毎月新しいロギングテーブルを作成すると同時に、古いロギングテーブルのUNION ALLであるログVIEWを作成することができます。最も適切なソースに対してレポートを実行します。

単一の(小さな)トランザクションで複数のログメッセージをフラッシュし、10個のスレッドが作業とログを処理している場合、1つのスレッドだけがログテーブルに内容をフラッシュするという利点があります。このパイプライニングは、実際には規模をより良くします。

関連する問題