Este artigo é um artigo espelhado de tradução automática, por favor clique aqui para ir para o artigo original.

Vista: 42676|Resposta: 4

[Fonte] Lidar com a distinção concorrente entre Timestamp e Concurrency Check

[Copiar link]
Publicado em 08/04/2017 00:10:50 | | | |


Autorwww.itsvse.com @小渣渣 !
Insira os dados base com sucesso!
O teste do recurso ConcurrencyCheck está concluído
Atualização bem-sucedida! Nota 1
A atualização é excepcional! Nota 2, informação anormal! Atualização de armazenamento, inserção ou exclusão da instrução afetou um número inesperado de linhas (0). As entidades podem ter sido modificadas ou excluídas desde que as entidades foram carregadas. Veja http://go.microsoft.com/fwlink/?LinkId=472540 para informações sobre como entender e lidar com exceções de concorrência otimista.

Teste a diferença entre Timestamp e ConcurrencyCheck
Atualização do UpdateTab1 bem-sucedida! Nome 1
Atualização do UpdateTab2 bem-sucedida! Nome 1
Atualização Tab2 é anormal! Nome 2, informação anormal! Atualização de armazenamento, inserção ou exclusão da instrução afetou um número inesperado de linhas (0). As entidades podem ter sido modificadas ou excluídas desde que as entidades foram carregadas. Veja http://go.microsoft.com/fwlink/?LinkId=472540 para informações sobre como entender e lidar com exceções de concorrência otimista.
Atualização do UpdateTab1 bem-sucedida! Nome 2

【TimeStamp】
O recurso TimeStamp pode ser aplicado à classe de campo, que possui apenas uma propriedade de array de bytes, e esse recurso define o tipo tiemStamp para a coluna. Em verificações simultâneas, o Code-First usa automaticamente esse campo do tipo TimeStamp.

【Concurrency Check】
A funcionalidade ConcurrencyCheck pode ser aplicada às propriedades de uma classe de domínio. Quando o EF realiza uma operação de atualização, o Code-First coloca o valor da coluna na instrução condição where, e você pode usar esse recurso CurrencyCheck para usar as colunas existentes para verificação de concorrência, em vez de usar uma coluna TimeStamp separada para verificação de concorrência.

Vamos começar criando um novo objeto de contexto para demonstrar a diferença entre Timestamp e ConcurrencyCheck no processamento de concorrência!

Aqui está o código para o contexto:




Vamos dar uma olhada nas colunas do banco de dados, da seguinte forma:



Vamos descobrir que tab1 e tab2 têm colunas Id, Nome e Observação, e tab2 tem mais colunas RowVersion do que tab1.

Anexe primeiro o código do teste:



【Princípio do Verificador de Concorrência】



Adicionamos o recurso ConcurrencyCheck à propriedade Remark do Tab1,


Quando atualizamos o valor do atributo Nome dos mesmos dados ao mesmo tempo, nenhuma exceção é lançada!


Gerar instruções SQL:


executivo sp_executesql N'UPDATE [dbo]. [Tab1]
SET [Nome] = @0
ONDE (([Id] = @1) E ([Observação] = @2))
',N'@0 nvarchar(max) ,@1 int,@2 nvarchar(max) ',@0=N'name1',@1=1,@2=N'Note1'
executivo sp_executesql N'UPDATE [dbo]. [Tab1]
SET [Nome] = @0
ONDE (([Id] = @1) E ([Observação] = @2))
',N'@0 nvarchar(max) ,@1 int,@2 nvarchar(max) ',@0=N'name2',@1=1,@2=N'note1'

Quando atualizamos o valor da propriedade Remark dos mesmos dados ao mesmo tempo, lançamos uma exceção!

Gerar instruções SQL:

executivo sp_executesql N'UPDATE [dbo]. [Tab1]
SET [Observação] = @0
ONDE (([Id] = @1) E ([Observação] = @2))
',N'@0 nvarchar(max) ,@1 int,@2 nvarchar(max) ',@0=N'Note1',@1=1,@2=N'Note'
executivo sp_executesql N'UPDATE [dbo]. [Tab1]
SET [Observação] = @0
ONDE (([Id] = @1) E ([Observação] = @2))
',N'@0 nvarchar(max) ,@1 int,@2 nvarchar(max) ',@0=N'Note 2',@1=1,@2=N'Note'

Podemos descobrir que, se pegarmos o mesmo dado com Id 1 ao mesmo tempo, obteremos o valor do atributo Remark, e ao atualizar o atributo Remark, usaremos Remark como condição de atualização.

A primeira instrução sql pode ser atualizada com sucesso, e então a observação é alterada para "nota 1", e quando a segunda instrução SQL é atualizada, a atualização falha porque o valor da observação mudou.

【Princípio do Timestamp】

Adicionamos uma propriedade RowVersion ao Tab2 (você pode escolher qualquer nome) e adicionamos o recurso Timestamp!!



Quando atualizamos o valor Nome dos mesmos dados ao mesmo tempo, a primeira atualização é bem-sucedida, a segunda falha e uma exceção é lançada, vamos dar uma olhada no código SQL gerado!

executivo sp_executesql N'UPDATE [dbo]. [Tab2]
SET [Nome] = @0
ONDE ((([Id] = @1) E ([RowVersion] = @2)) E ([Observação] = @3))
SELECT [RowVersion]
DE [dbo]. [Tab2]
ONDE @@ROWCOUNT > 0 E [Id] = @1',N'@0 nvarchar(max), @1 int,@2 binary(8),@3 nvarchar(max) ',@0=N'Name1',@1=1,@2=0x00000000000007D1,@3=N'Note'
executivo sp_executesql N'UPDATE [dbo]. [Tab2]
SET [Nome] = @0
ONDE ((([Id] = @1) E ([RowVersion] = @2)) E ([Observação] = @3))
SELECT [RowVersion]
DE [dbo]. [Tab2]
ONDE @@ROWCOUNT > 0 E [Id] = @1',N'@0 nvarchar(max), @1 int,@2 binary(8),@3 nvarchar(max) ',@0=N'name2',@1=1,@2=0x00000000000007D1,@3=N'Note'

Ao executar a segunda instrução SQL, como os dados da condição where não podem mais ser encontrados, a atualização falha e uma exceção é lançada!!

Após a execução com sucesso da primeira instrução sql, o valor de RowVersion mudará, como mostrado na figura abaixo:





RowsVersion é timestamp

Solução alternativa para atualizações ausentes   

Conceito de atualizações ausentes: Quando os usuários modificam uma linha de dados ao mesmo tempo, eles primeiro leem os dados, os colocam na interface para modificação e então enviam os dados quando modificados, de modo que os dados finais submetidos sobrescrevam os dados previamente enviados, causando a atualização perdida.

Resumindo, aqui estão maneiras de evitar perder atualizações:

Use o carimbo de data do RowsVersion.

Se uma linha for inconsistente com o valor antes da leitura, significa que outra transação atualizou essa coluna, de modo que ela não pode ser atualizada, prevenindo assim a perda das atualizações.



Por fim, anexe o código-fonte:
CodeFirstDemo.rar (4.94 KB, Número de downloads: 13)




Anterior:Política de geração de chaves primárias nativas Nhibernate
Próximo:O EF6 usa o Database.BeginTransaction para gerenciar transações
Publicado em 22/03/2022 11:51:38 |
Obrigado pelo trabalho duro, muito bom post
 Senhorio| Publicado em 01/11/2023 20:42:15 |
Exceção de concorrência EF DbUpdateConcurrencyException consulta o valor em cache
https://www.itsvse.com/thread-10692-1-1.html
 Senhorio| Publicado em 27/12/2023 19:54:01 |
Declarações de migração geradas por rowversions otimistas de bloqueio do EF Core




Disclaimer:
Todo software, material de programação ou artigos publicados pela Code Farmer Network são apenas para fins de aprendizado e pesquisa; O conteúdo acima não deve ser usado para fins comerciais ou ilegais, caso contrário, os usuários terão todas as consequências. As informações deste site vêm da Internet, e disputas de direitos autorais não têm nada a ver com este site. Você deve deletar completamente o conteúdo acima do seu computador em até 24 horas após o download. Se você gosta do programa, por favor, apoie um software genuíno, compre o registro e obtenha serviços genuínos melhores. Se houver qualquer infração, por favor, entre em contato conosco por e-mail.

Mail To:help@itsvse.com