2016-08-08 11 views
1

このエラーが処理されていることは承知しております。SQL Server:デッドロックの犠牲者。トランザクションを再開してください

サードパーティのアプリケーションが所有するデータベース内のいくつかのテーブルでSELECTに限定されたアカウントがあります。私たちが第三者に要求しなくても、奇妙なことを安全に照会できるというアイデアは、私たちのために変更を加える(あまり反応しません)。

これは、私がログで例外を気付いた今日(郵便タイトルを参照)まで、(表面上)正常に動作しています。

クエリがあったことを考える:

SELECT 
    DATEDIFF(ss, '01-01-1970 00:00:00', (SELECT MAX(CREATEDDATE) 
             FROM VISITS 
             WHERE CUSTID = 31)) 

そしてDBCC USEROPTIONSは、なぜ何もして上記の競合がすべき、コミット分離レベルが読み取られた私に語ったこと?私はそれが時代遅れの価値を得ることを理解することができますが、なぜコミットのみの読み取りで競合?

とにかく、私の心配していることは、もう一方の側で起こっている可能性があることです。サードパーティのアプリが同様のエラーを経験しており、誰も気付いていないと(彼らは急いでいません)

誰もがもう一方の側について安心して(もう一度、私はSELECTをやっているだけです)、この種のシナリオではベストプラクティスについて助言してもらえますか? SQLの並行性は、私が過去にあまり心配していなかったことではありません。

おかげ

答えて

0

デッドロックのこの種は、多くの場合、影響を受けるテーブルとインデックスの値へのアクセスパスに関係しています。上記のクエリには集計(最大)が含まれていますので、最低限必要な場合は0にする必要があります。要求された顧客の行の中で最大値を見つけます。それをサポートするインデックスがあるかもしれません。ただし、検索中は、たとえ簡潔であっても、データを更新に対してロックする必要があります。同時に、更新クエリは異なるインデックスのシーケンスを使用してデータにアクセスすることになり、更新を可能にするために排他ロックが必要です。そう、はい、コミットされた孤立を読んで、ちょうど正しいアップデートと選択はデッドロックすることができます。

最高の長期的な解決策は、おそらくRCSI(Read Committed Snapshot Isolation)で、テーブルで変更されているライブ/ホット値ではなく、行の古いバージョンを使用することができます。あなたがサードパーティーのアプリを持っているならば、それをオンにする前に、ベンダーはその設定をテストしサポートする必要があります。それだけをオンにしないでください。それは素晴らしい機能ですが、特定のアプリのテストが必要です。つまり、通常は必要な変更は最小限に抑えられていますが、例外はありません。

このような実際のイベントからデッドロック・グラフを慎重に調べると、デッドロックを防ぐためにインデックスを変更することができます。

最後に、コミットされていないデータを読み取ることはできますが、結果は常に100%正確ではない可能性があります。

+0

ありがとうございました。私はSELECTだけで私は他のアプリの方法で取得していないと仮定安全ですか? – whoasked

+0

いいえ、あなたは本当にそれを仮定することはできません。すべてのデッドロック(アプリケーションと選択項目の両方)が安全な側にあるように、SQL Serverを監視することができます。 – onupdatecascade

+0

@oneupdatecascade Sql Serverのデッドロックを監視して、発生時にこれらをデバッグする方法を教えてください。すべてのポインタ?私はこれらのデッドロックを週に数回得る。 – mxmissile

関連する問題