У меня есть две тестовые транзакции в течение двух сеансов соответственно. Предполагая, что эти две транзакции будут выполняться одновременно. Я пытаюсь сделать так, чтобы одна транзакция вставляла номер счета правильно после выполнения другой транзакции. Нет дубликатов. Я сделал это, как показано ниже. Но если я удалю с (tablockx) в сеансе 2, они больше не будут работать. Я проверил в строке книги, но не ответил. Кто-нибудь поможет? Serializable не будет работать, поскольку два SELECT хотят быть эксклюзивными друг для друга здесь. Благодарю.Следует ли указывать tablockx в каждом сеансе?
В сессии 1:
begin transaction
declare @i int
select @i=MAX(InvNumber) from Invoice
with(tablockx)
where LocName='A'
waitfor delay '00:00:10'
set @[email protected]+1
insert into Invoice values('A',@i);
commit
В сессии 2:
begin transaction
declare @i int
select @i=MAX(InvNumber) from Invoice
with(tablockx)
where LocName='A'
set @[email protected]+1
insert into Invoice values('A',@i);
commit
(UPDLOCK, HOLDLOCK) не работает, так как номер счета-фактуры генерируется для двух сеансов. – FebWind
@FebWind - Если вы используете его внутри транзакции, так как мой ответ невозможен. 'HOLDLOCK' всегда блокирует по крайней мере весь диапазон, указанный в запросе, и невозможно, чтобы две параллельные транзакции имели' UPDLOCK' на том же ресурсе. –
@FebWind - И это легко увидеть в SSMS. Просто откройте два окна. И выполните следующие действия: «BEGIN TRANSACTION DECLARE @i INT SELECT @i = MAX (InvNumber) FROM Invoice WITH (UPDLOCK, HOLDLOCK) WHERE LocName =« A »вторая транзакция будет заблокирована« выполнение запроса », ожидающая первого пока вы не вернетесь в первое окно и не выполните «COMMIT» или «ROLLBACK» –