Pergunta

Eu tenho um problema de impasse com duas transações que não acessam nenhum registro comum. Também não há escalada de bloqueio. Portanto, não posso explicar por que um impasse é possível.

O impasse ocorre quando duas dessas transações são executadas ao mesmo tempo:

begin transaction

update A set [value] = [value]
where id = 1; /* resp. 2 */

/* synchronize transactions here */

SELECT * 
FROM  
 A inner join B on A.B_FK = B.id
 inner join C on C.A_FK = A.id
WHERE 
 A.[value] = 1; /* resp. 2 */

rollback;

Estas são as tabelas e dados para configurar o cenário:

CREATE TABLE A (
  id INT NOT NULL,
  [value] INT,
  B_FK INT
  primary key (id)
)

CREATE TABLE B (
  id INT NOT NULL,
  primary key (id)
)

CREATE TABLE C (
  id INT NOT NULL,
  A_FK INT
  primary key (id)
)

INSERT INTO A VALUES(1, 1, 1) 
INSERT INTO B VALUES(1) 
INSERT INTO C VALUES(1, 1) 

INSERT INTO A VALUES(2, 2, 2) 
INSERT INTO B VALUES(2) 
INSERT INTO C VALUES(2, 2) 

Mesa A está no meio de três mesas. Se eu mudar alguma coisa na consulta, por exemplo, remova uma das mesas unidas B ou C, não há impasse. O mesmo quando eu filtro A.id ao invés de A.value.

O deadlock-Graph me diz que ambos querem definir uma trava para o índice de chave primária da tabela A. Novamente: não há escalada de bloqueio.

Estou usando o SQLSERVER 2005.

  • Por que essas transações estão conflitantes sem acessar dados comuns? Alguém pode explicar isso?
  • O que posso fazer para evitar isso? Estou usando o Nibernate e não posso alterar a consulta tão facilmente.
  • Poderia ser um problema do SQLServer?

Muito obrigado.

Foi útil?

Solução

O conflito pode acontecer, porque o SQL-Server faz o bloqueio não apenas no nível da linha, mas também na página ou no nível da tabela.

Isso significa que um registro pode ser bloqueado, mesmo que não esteja realmente em uso, mas apenas um registro diferente "próximo".

Contenção de bloqueio do servidor SQL domada pode ser útil

Outras dicas

Além disso, outra coisa a considerar quando você às vezes obtém esses problemas é que o bloqueio pode vir do processamento feito por gatilhos.

Licenciado em: CC-BY-SA com atribuição
Não afiliado a StackOverflow
scroll top