EntityConnection 只能用封闭的 DbConnection 来构造

发布于 2024-12-01 07:52:12 字数 1322 浏览 2 评论 0原文

“EntityConnection 只能用封闭的 DbConnection 来构造” 这是我在尝试构建提供开放连接的实体连接时遇到的问题。 有一个打开的事务范围,我不想打开一个新连接,否则该事务将被提升为 dtc 事务,因为我的理解是,如果我在多个实体连接上使用单个 SqlConnection,我不需要 DTC。

所以,我的代码大约是这样的。

提前致谢...

    using (TransactionScope transactionScope = new TransactionScope())
{

    using (SqlConnection dwConn = GetDWConnection(user)) 
    {
        dwConn.Open();
        // I need to do some SQlConnection specific actions first

        //EntityConnection specific actions next
        Func1(dwConn);
        Func2(dwConn); //similar to Func1()
        Func3(dwConn); //Similar to Func1()

    }

}
    Func1(SqlConnection dwConn)
    {
        using (EntityConnection conn = GetSQLEntityConnection(sqlConnection))
        {
            ObjectContext objectContext = (ObjectContext)Activator.CreateInstance(objectContextType, new object[] { conn });
            //few actions
        }
    }
    private EntityConnection GetSQLEntityConnection(SqlConnection sqlConnection)
        {
        //few steps
            EntityConnection entityConnection = new EntityConnection(entityConnectionStringBuilder.ToString());

            EntityConnection sqlEntityConnection = new EntityConnection(entityConnection.GetMetadataWorkspace(),sqlConnection);
            return sqlEntityConnection;
        }

"EntityConnection can only be constructed with a closed DbConnection"
This is the problem I get when a try to construct an entityconnection providing an open connection.
There is a transactionscope open and I don't want to open a new connection or the transaction would be promoted to a dtc transaction as my understanding is that if I use a single SqlConnection over the multiple entityConnections, I don't need DTC.

So, my code is approximately like this.

Thanks in advance...

    using (TransactionScope transactionScope = new TransactionScope())
{

    using (SqlConnection dwConn = GetDWConnection(user)) 
    {
        dwConn.Open();
        // I need to do some SQlConnection specific actions first

        //EntityConnection specific actions next
        Func1(dwConn);
        Func2(dwConn); //similar to Func1()
        Func3(dwConn); //Similar to Func1()

    }

}
    Func1(SqlConnection dwConn)
    {
        using (EntityConnection conn = GetSQLEntityConnection(sqlConnection))
        {
            ObjectContext objectContext = (ObjectContext)Activator.CreateInstance(objectContextType, new object[] { conn });
            //few actions
        }
    }
    private EntityConnection GetSQLEntityConnection(SqlConnection sqlConnection)
        {
        //few steps
            EntityConnection entityConnection = new EntityConnection(entityConnectionStringBuilder.ToString());

            EntityConnection sqlEntityConnection = new EntityConnection(entityConnection.GetMetadataWorkspace(),sqlConnection);
            return sqlEntityConnection;
        }

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(2

ゃ人海孤独症 2024-12-08 07:52:12

雅库布是完全正确的。您既不能创建 DbContext 也不能创建 EntityConnection 并将打开的 DbConnection 传递给它们。

根据 Diego B Vega 的帖子 此问题在 EF 6 发布之前不会得到修复 (这里你可以投票)

解决方法是在之前打开已经初始化的EntityConnection任何涉及它的操作。

给定ObjectContext,您可以像这样打开EntityConnection

((EntityConnection)objectContext.Connection).Open();

DbContext的情况下,EntityConnection可从底层获得对象上下文。代码可能是这样的:

class MyDbContext : DbContext
{
    public MyDbContext (DbConnection connection) 
                  : base (connection, contextOwnsConnection: true)
    {
        ((IObjectContextAdapter)this).ObjectContext.Connection.Open();
    }

    // …
}

class Program
{
    public static void Main()
    {
        var connection = new SqlConnection(CONNECTION_STRING);
        using (var database = new MyDbContext(connection))
        {
            Assert.IsTrue(connection.State == ConnectionState.Open);
        }
        Assert.IsTrue(connection.State == ConnectionState.Closed);
    }
}

Jakub is completely right. You can create neither DbContext nor EntityConnection with opened DbConnection passed to them.

According to Diego B Vega’s post this issue will not be fixed until EF 6 release (here you can vote for it)

The workaround is to open already initialized EntityConnection before any operations involving it.

Given ObjectContext you can open EntityConnection like this:

((EntityConnection)objectContext.Connection).Open();

In case of DbContext the EntityConnection is available from underlying ObjectContext. The code might be like this:

class MyDbContext : DbContext
{
    public MyDbContext (DbConnection connection) 
                  : base (connection, contextOwnsConnection: true)
    {
        ((IObjectContextAdapter)this).ObjectContext.Connection.Open();
    }

    // …
}

class Program
{
    public static void Main()
    {
        var connection = new SqlConnection(CONNECTION_STRING);
        using (var database = new MyDbContext(connection))
        {
            Assert.IsTrue(connection.State == ConnectionState.Open);
        }
        Assert.IsTrue(connection.State == ConnectionState.Closed);
    }
}
天荒地未老 2024-12-08 07:52:12

正如您已经发现的,您无法从打开的连接创建新的 EntityConnection

您应该重构代码并传递 ObjectContext,而不是一遍又一遍地传递 SqlConnection 和创建 EntityConnectionObjectContext 是 EF 中的根对象,您应该更喜欢它而不是 SqlConnection

As you've already found out, you cannot create a new EntityConnection from an opened connection.

Instead of passing SqlConnection around and creating EntityConnection over and over again you should refactor your code and pass ObjectContext instead. ObjectContext is the root object in EF and you should favour it over SqlConnection.

~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文