基本的に、従来のキュー ベースのワークフローについて説明しているため、実際の の使用を検討する必要があります。キュー .
議論のために、あなたが望むものを達成する方法は次のとおりです:
- 特定のリソースを要求:
SELECT ... FROM resources WITH (UPDLOCK, ROWLOCK) WHERE key =@key
.リソースがすでに要求されている場合はブロックします。リソースがすでに要求されている場合は、ロック タイムアウトを使用して例外を返します。キー
しなければならない 索引付けされ、一意であること。 - 次に利用可能なリソース:
SELECT ... FROM resources WITH (UPDLOCK, ROWLOCK, READPAST) ORDER BY
.リソースの優先度 (最も古い、最も高い優先度など) を表すには、順序を定義する必要があります - 要求されたリソースを解放する:
COMMIT
あなたの取引
問題の要点は正しいロック ヒントを使用することであり、この種の問題を解決するには明示的なロック ヒントが必要です。 UPDLOCK は「要求」ロックとして機能します。 ROWLOCK は、サーバーがページ ロックに「最適化」するのを防ぐ適切な粒度を作成します。 READPAST を使用すると、要求されたリソースをスキップできます。行に UPDLOCK を配置すると、行がロックされ、後で更新できるようになりますが、ロックされた行でブロックされる通常の読み取りコミット SELECT などの他の操作が妨げられます。アイデアは、行をとにかく更新しようとしているということですが、これにより、避けられない X ロックが配置されます。テーブルの可用性を高めたい場合は、アプリ ロック 代わりに、正しく引き離すのが非常に困難です。キー値などのリソースの文字列記述子または CHECKSUM
でアプリ ロックを要求する必要があります。 キーのロックレス%%
価値。アプリ ロックを使用すると、「セッション」スコープでアプリ ロックを要求することにより、「クレーム」のスコープをトランザクションから分離できますが、クレームを手動で解放する必要があります (「トランザクション」スコープのアプリ ロックはコミット時に解放されます)。 .ただし注意してください。アプリのロックで足を撃つ方法は無数にあります。