EF架构~关系表插入应该写在事务里,但不应该是分布式事务

简介:

这个标题很有意思,关系表插入,就是说主表和外表键在插入时,可能会有同步插的情况,如在建立主表时,扩展表需要同步完成数据的初始化工作,而对于多表插入时,我们为了保证数据的一致性会针它写在事务中,而对于.net中的事件,它在一些情况下,会不那么单纯,对于ef和linq to sql来说,你的事务如果出现多次提交动作(submitchange | savechanges),那么,.net这边会把它提升为分布式事务(MSDTC),即.net认为,对于一个数据表的操作,不会出现多个savechanges,OK,这个可以解释的通,一个数据库,一个提交,这是符合性能要求的,呵呵,但对于我们的架构来说,有时一疏忽,就违背了.net的这个原则,如,我们封装的Insert方法,可能是这样的

   public virtual void Insert(TEntity item)
        {
       
            Db.Entry<TEntity>(item);
            Db.Set<TEntity>().Add(item);
            this.SaveChanges();
           
        }

这个代码也没有问题,在一个插入动作完成后,系统由SaveChanges方法完成一次提交,正是由于这样的代码,所以我们的麻烦就来了,如果是对两个表的操作吗?

aRepository.Insert(a);
bRepository.Insert(b);

什么问题?数据一致性不能保证,因为没有事务块,呵呵,加上了再看看

  using (TransactionScope trans = new TransactionScope())
{
  aRepository.Insert(a);
  bRepository.Insert(b);
  trans.Commit();
}

OK,感觉是没有问题了,但细一想就会看出问题来了,因为我们封装的insert会有提交动作,所以,在这个事务块中,.net会被认识是一个MSDTC(分布式的事务),原因是提交了多次,而如果你没有打开msdtc服务的话,就会出现下面的黄屏了

注意:系统触发分布式事务的前提是你的WEB服务器与数据库服务器分别部署在两个服务器上,一台不会出现这个问题的。

OK,这个MSDTC是怎么一回事,不是今天要说的重要,如果想学习MSDTC,请看我的这些文章:

 

第二十六回   将不确定变为确定~transactionscope何时提升为分布式事务?

第二十七回   将不确定变为确定~transactionscope何时提升为分布式事务~续

第二十八回   将不确定变为确定~transactionscope何时提升为分布式事务~再续(避免引起不必要的MSDTC)

第二十九回    将不确定变为确定~transactionscope何时提升为分布式事务~大结局

今天我们要说的是在插入关系表时,怎样使它不被提升为分布式事务,事实上,怎么做我们已经知道了,就是方法中只出现一个savechages,呵呵,而对于主表与扩展表来说,对于自增主键的主表,做起来就有些麻烦了,呵呵,我们还需要借助SQL函数来实现主键的获取工作,当主键插入后,通过SQL函数得到新值,然后再为扩展表赋值,最后一些savechange()就可以了,具体我们看一下代码:

  int maxID = Convert.ToInt32(new TsingDa_NewLearningBarEntities()//当前表最大ID
                  .Database.SqlQuery<decimal>("SELECT IDENT_CURRENT ('Classroom_Info')")
                  .First());
            using (TransactionScope trans = new TransactionScope())
            {
                try
                {
                    db.Entry<Classroom_Info>(entity);
                    db.Set<Classroom_Info>().Add(entity);

                    //绑定学生
                    entity.User_Classroom_R.ToList().ForEach(i =>
                    {
                        i.ClassroomInfoID = maxID + 1;
                        db.Entry<User_Classroom_R>(i);
                        db.Set<User_Classroom_R>().Add(i);
                    });
                    db.SaveChanges();//是否为msdtc就看它提交的次数
                    trans.Complete();
                }
                catch (Exception)
                {
                    trans.Dispose();//出现异常,事务手动释放
                    throw;
                }
            }

而一次savechanges所产生的SQL也是我们可以接受的,与服务器连接池中开启一个新连接,然后把语句一条一条的发过去,虽然不是一次性发送,但结果我们也是可以接受的,呵呵。

 

补充回复:

看了xiashengwang的 回复,我自己去试了一下,果然savechange将当前上下文中所有要提交的东西包在了一个事务块里,出现异常后,自动完成callback,所以,对 于一个数据库来说TransactionScope可以省去,而对于多个数据库的操作,才需要使用TransactionScope,而对于何时将 TransactionScope提升为MSDTC的级别,到目前为止,我只能说,一个上下文的savechanges不会提升,多个 savechanges就会提升到msdtc,而矛盾是,一个savechanges的话,确实不需要外加TransactionScope块了,呵呵, 这部分文章估计我还要继续写了,看看有没有办法在同一上下文多个savechanges操作时,不让系统提升到MSTDC的级别,呵呵。

本文转自博客园张占岭(仓储大叔)的博客,原文链接:EF架构~关系表插入应该写在事务里,但不应该是分布式事务,如需转载请自行联系原博主。

目录
相关文章
|
2月前
|
SQL 关系型数据库 MySQL
乐观锁在分布式数据库中如何与事务隔离级别结合使用
乐观锁在分布式数据库中如何与事务隔离级别结合使用
|
3天前
|
SQL 关系型数据库 MySQL
乐观锁在分布式数据库中如何与事务隔离级别结合使用
乐观锁在分布式数据库中如何与事务隔离级别结合使用
|
1月前
|
安全 应用服务中间件 API
微服务分布式系统架构之zookeeper与dubbo-2
微服务分布式系统架构之zookeeper与dubbo-2
|
1月前
|
负载均衡 Java 应用服务中间件
微服务分布式系统架构之zookeeper与dubbor-1
微服务分布式系统架构之zookeeper与dubbor-1
|
1月前
|
存储 JSON 数据库
Elasticsearch 分布式架构解析
【9月更文第2天】Elasticsearch 是一个分布式的搜索和分析引擎,以其高可扩展性和实时性著称。它基于 Lucene 开发,但提供了更高级别的抽象,使得开发者能够轻松地构建复杂的搜索应用。本文将深入探讨 Elasticsearch 的分布式存储和检索机制,解释其背后的原理及其优势。
142 5
|
2天前
|
消息中间件 关系型数据库 Java
‘分布式事务‘ 圣经:从入门到精通,架构师尼恩最新、最全详解 (50+图文4万字全面总结 )
本文 是 基于尼恩之前写的一篇 分布式事务的文章 升级而来 , 尼恩之前写的 分布式事务的文章, 在全网阅读量 100万次以上 , 被很多培训机构 作为 顶级教程。 此文修改了 老版本的 一个大bug , 大家不要再看老版本啦。
|
6天前
|
存储 安全 API
单元化架构,分布式系统的新王!
【10月更文挑战第9天】
48 0
单元化架构,分布式系统的新王!
|
1月前
Saga模式在分布式系统中如何保证事务的隔离性
Saga模式在分布式系统中如何保证事务的隔离性
|
13天前
|
存储 SQL 消息中间件
Hadoop-26 ZooKeeper集群 3台云服务器 基础概念简介与环境的配置使用 架构组成 分布式协调框架 Leader Follower Observer
Hadoop-26 ZooKeeper集群 3台云服务器 基础概念简介与环境的配置使用 架构组成 分布式协调框架 Leader Follower Observer
34 0
|
2月前
|
存储 NoSQL Java
一天五道Java面试题----第十一天(分布式架构下,Session共享有什么方案--------->分布式事务解决方案)
这篇文章是关于Java面试中的分布式架构问题的笔记,包括分布式架构下的Session共享方案、RPC和RMI的理解、分布式ID生成方案、分布式锁解决方案以及分布式事务解决方案。
一天五道Java面试题----第十一天(分布式架构下,Session共享有什么方案--------->分布式事务解决方案)

热门文章

最新文章