今、私は(コメントから)あなたの特定のビジネスシナリオが何であるかを知っていることは、ここであなたは、これがあることをシリアライズ可能分離に
CREATE PROCEDURE [dbo].[updateUserState] (@UserID int)
AS
BEGIN
SET TRANSACTION ISOLATION LEVEL READ COMMITTED;
BEGIN TRANSACTION
SELECT [State]
FROM [dbo].[UserState] WITH (UPDLOCK)
WHERE [UserID] = @UserID;
IF ([State] = 'logged out')
BEGIN
UPDATE [us]
SET [State] = 'logged in'
FROM [dbo].[UserState] AS [us]
WHERE [UserID] = @UserID;
END
COMMIT TRANSACTION
END
注意を実装することなく、あなたが提案しているもののような何かをしたい方法です簡略化されていますが、主なアイデアを提示しますSELECT
ステートメントのUPDLOCK
ヒントが鍵です。 「私は更新を行うつもりでデータを選択しようとしています(直後です)、トランザクションが終了するまでそれを保持してください」というメッセージが表示されます。あなたの例では、T2が来て、T1がまだ動いているならば、T2は更新ロックを得ることができないので、T1が完了するまで待つでしょう。また、トランザクション分離レベルを明示的に設定することは完全性のためのものであり、 READ COMMITTED
がSQL Serverの既定値です。
私が本当に必要とするのは、最後にコミットされたレコードの状態を返すことです。基本的には、完全性については気にしません。 – NullReference
それはちょうどときどきです。たとえば、ある行の状態を更新する関数があり、呼び出されたときに他のトランザクションがそのレコードを読み取ったり更新したりしないようにします。今私は現在のステータスを照会する必要があり、私はまったくデータの整合性を気にしません。 – NullReference
MSSQLデータベース。 – NullReference