我有一个命令服务类,它利用工作单元模式,通过各种方法通过实体框架更新数据库(在本例中为SQL Azure)。
命令服务通过对dbcontext实例的引用进行实例化,dbcontext的生命周期由我选择的DI框架管理。
一些命令服务类'方法在事务中包装对数据库的多个更新,例如:
public void UpdateStuff(someEntity)
{
using(var tx = _db.Database.BeginTransaction())
{
//Some updates to db
_db.SaveChanges();
//Some other updates to db
_db.SaveChanges();
tx.Commit();
}
}
现在,其中一些方法在其事务中调用命令类的其他方法,例如:
public void UpdateWithSomeCascadingStuff(someOtherEntity)
{
using(var tx = _db.Database.BeginTransaction())
{
//Some updates to db
_db.SaveChanges();
//Some other cascading logic and updates to db
var relatedEntityToUpdate = _query.GetSomeEntityToUpdate(someOtherEntity);
UpdateStuff(relatedEntityToUpdate);
_db.SaveChanges();
tx.Commit();
}
}
显然,通过这样做,我正在为同一个DbContext实例嵌套EF事务。
这是否受到支持并会引起任何麻烦?我可以选择其他方法吗?
更新: 我正在使用EF6 Code First
答案 0 :(得分:2)
EntityFramework的DBContexts本身实现了UnitOfWork和Repository模式。
EF6中的上下文也会自动包装事务中的所有提交(如果它还不是其中的一部分)。
所以,不,你不应该在多个工作单元之间共享一个上下文。他们应该各自得到自己的。
<强>更新强>
如果您尝试在同一个DbContext上启动重复交易,则会获得:
An unhandled exception of type 'System.InvalidOperationException' occurred in EntityFramework.dll
Additional information: The connection is already in a transaction and cannot participate in another transaction. EntityClient does not support parallel transactions.
所以不,你不能做你想要的。