Como reverter uma transação no Entity Framework
-
21-08-2019 - |
Pergunta
string[] usersToAdd = new string[] { "asd", "asdert", "gasdff6" };
using (Entities context = new Entities())
{
foreach (string user in usersToAdd)
{
context.AddToUsers(new User { Name = user });
}
try
{
context.SaveChanges(); //Exception thrown: user 'gasdff6' already exist.
}
catch (Exception e)
{
//Roll back all changes including the two previous users.
}
Ou talvez isso é feito automaticamente, o que significa que se ocorrer um erro, as mudanças que cometem são cancelados para todas as mudanças. é?
Solução
OK
Eu criei uma amostra de uma aplicação como o exemplo da questão e afterwords I verificados no DB e foram adicionados nenhum usuário.
Conclusão:. ObjectContext.SaveChange é automaticamente uma transação
Nota:. Eu acredito transações será necessário se executar sprocs etc
Outras dicas
Eu acredito (mas não sou especialista muito tempo na EF) que até a chamada para context.SaveChanges atravessa, a transação não foi iniciado. Eu esperaria uma Exceção de que a chamada seria automaticamente reverter qualquer transação começou. Alternativas (em caso de você querer estar no controle da transação) [a partir "Programação Entity Framework" da J.Lerman O'Reilly, pg. 618]
using (var transaction = new System.Transactions.TransactionScope())
{
try
{
context.SaveChanges();
transaction.Complete();
context.AcceptAllChanges();
}
catch(OptimisticConcurrencyException e)
{
//Handle the exception
context.SaveChanges();
}
}
ou
bool saved = false;
using (var transaction = new System.Transactions.TransactionScope())
{
try
{
context.SaveChanges();
saved = true;
}
catch(OptimisticConcurrencyException e)
{
//Handle the exception
context.SaveChanges();
}
finally
{
if(saved)
{
transaction.Complete();
context.AcceptAllChanges();
}
}
}