8

Całkiem proste pytanie. W SQL 2008, jeśli mam procedurę przechowywaną (patrz niżej), czy ryzykuje się stan wyścigu między dwoma pierwszymi stwierdzeniami, czy procedura przechowywana blokuje rzeczy, które dotyka, tak jak robią to transakcje?Czy procedury przechowywane blokują tabele/wiersze?

ALTER PROCEDURE [dbo].[usp_SetAssignedTo] 
    -- Add the parameters for the stored procedure here 
    @Server varchar(50), 
    @User varchar(50), 
    @UserPool varchar(50) 
AS 
BEGIN 
    SET NOCOUNT ON; 
    Declare @ServerUser varchar(50) 

    -- Find a Free record 
    SELECT top 1 @ServerUser = UserName 
    from ServerLoginUsers 
    where AssignedTo is null and [TsServer] = @Server 

    --Set the free record to the user 
    Update ServerLoginUsers 
    set AssignedTo = @User, AssignedToDate = getdate(), SourcePool = @UserPool 
    where [TsServer] = @Server and UserName = @ServerUser 

    --report record back if it was updated. Null if it was not available. 
    select * 
    from ServerLoginUsers 
    where [TsServer] = @Server 
     and UserName = @ServerUser 
     and AssignedTo = @User 
END 

Odpowiedz

3

Możesz uzyskać warunki wyścigu.

To może być wykonane w jednym stwierdzeniem:

  • można przypisać w aktualizacji
  • wskazań lock umożliwić inny proces pominąć ten wiersz
  • się pkt Wyjście danych wraca do rozmówcy

Spróbuj tego ... (edit: usunięty HOLDLOCK)

Update TOP (1) ServerLoginUsers WITH (ROWLOCK, READPAST) 
OUTPUT INSERTED.* 
SET 
    AssignedTo = @User, AssignedToDate = getdate(), SourcePool = @UserPool 
WHERE 
    AssignedTo is null and [TsServer] = @Server -- not needed -> and UserName = @ServerUser 

Jeśli nie, być może trzeba osobny wybierz

Update TOP (1) ServerLoginUsers WITH (ROWLOCK, READPAST) 
SET 
    -- yes, assign in an update 
    @ServerUser = UserName, 
    -- write 
    AssignedTo = @User, AssignedToDate = getdate(), SourcePool = @UserPool 
OUTPUT INSERTED.* 
WHERE 
    AssignedTo is null and [TsServer] = @Server -- not needed -> and UserName = @ServerUser 

SELECT ... 

Zobacz to proszę o więcej: SQL Server Process Queue Race Condition

+0

oświadczenie wyjście musi zostać wprowadzone po zbiorze do poprawnej składni –

+0

kiedyś swój pierwszy przykład ale dostałem błąd "Możesz określić blokadę READPAST na poziomie izolacji" ZAPOZNAJ ZOBOWIĄZANE lub POWTÓRZYJ CZYTAJ CZYTANIE ", gdy ją uruchomiłem. –

+0

Ah OK, upuść thw HOLDLOCK następnie – gbn