c# - EF Transactions C# MySQL 连接器

标签 c# mysql entity-framework-4 transactions transactionscope

我想知道实现以下内容的最佳方法或实践是什么:

我有一个名为 EditUser 的方法,它具有以下定义:

public void EditUser(user user, Roles role)
    {
        using (TestEntities entities = new TestEntities())
        {
            entities.Connection.Open();
            using (DbTransaction trans = entities.Connection.BeginTransaction())
            {
                try
                {
                    var tmpUser = entities.users.Where(fields => fields.UserId == user.UserId).FirstOrDefault();

                    RoleManagement rm = new RoleManagement();
                    string oldRole = tmpUser.roles.FirstOrDefault().Name;
                    string newRole = rm.GetRoleName(role);

                    if (oldRole == newRole)
                    {
                        entities.users.ApplyCurrentValues(user);
                    }
                    else
                    {
                        rm.UnbindRoles(tmpUser.UserId, entities.Connection);
                        this.DeleteUser(tmpUser.UserId, entities.Connection);
                        this.Register(user, role, entities.Connection);
                    }

                    entities.SaveChanges();
                    trans.Commit();
                }
                catch (Exception ex)
                {
                    trans.Rollback();
                    throw ex;
                }
            }
        }
    }

您可能会注意到,我正在调用几种方法:UnbindRoles、DeleteUser 和 RegisterUser,其中所有这些方法都需要在同一事务(EditUser 正在运行的同一事务)下运行,以防出现故障,我需要回滚。

现在我的问题主要出在这里...RegisterUser 方法也会启动一个新事务,因为它添加了一个用户并为新用户分配了一个角色。

任何人都可以描述如何实现这一点的最佳方法吗?我尝试使用 TransactionScope block ,但它失败了,因为我在中等信任环境中运行此应用程序

编辑

确认 MySQL .NET 连接器提供程序在中等信任下使用 TransactionScope 时存在错误,因为我刚刚使用 MS SQL Server 数据库测试了相同的场景,并且它可以正常工作,没有任何问题

最佳答案

如果我理解正确的话,您遇到的问题是您对 DeleteUser 和 RegisterUser 的调用正在启动新事务,并且需要加入当前事务。

解决此问题的几种方法:

A) 当您创建事务范围时,您可以说,如果没有可用的事务范围,他们只需创建一个。

B)不采用第一种方法,而是引入私有(private)方法,让我们假设 InnerEdit 和 InnerRegister 包含逻辑,但不打开或关闭代码保留在公开可用的 Edit 和 Register 方法中的任何事务。这些“内部”方法可以重用,而公共(public)方法则包含基础设施。如果您要使用谷歌的第二种方法进行面向方面的编程,则可以解决这些“横切问题”

public void EditUser(user user, Roles role)
{
    using (TestEntities entities = new TestEntities())
    {
        entities.Connection.Open();
        using (DbTransaction trans = entities.Connection.BeginTransaction())
        {
          InnerEditUser(entities, trans);
          InnerThat(entities, trans);
          InnerThis(entities,trans);
          entities.SaveChanges();
          trans.Commit();
        }
    }
 }

TransactionScope options MSDN link

关于c# - EF Transactions C# MySQL 连接器,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/6761891/

相关文章:

c# - 使用 AJAX 上传文件

c# - 如何将数据从 Controller 操作传递到布局模板中的子操作?

mysql — 返回未被其他人更新的行

mysql - 更高效的 SQL 查询结构

mysql - 我无法看到我的 mysql 数据库中任何表的外键

c# - LINQ to Entities 使用 .date 分组失败

c# - 如何在 C# 应用程序中使用 FluentValidation

dictionary - 带有字典的 Entity Framework 4 POCO

entity-framework-4 - 从没有系统表的数据库更新模型?

c# - 南希代理请求