微信公众号搜"智元新知"关注
微信扫一扫可直接关注哦!

在 .NET Core 3.x 的上下文中运行 EF6“SqlQuery<T>()”的问题

如何解决在 .NET Core 3.x 的上下文中运行 EF6“SqlQuery<T>()”的问题

我有一个 .NET Framework 4.x 类库,它利用了 Entity Framework 6。直到最近它才被用于另一个基于 4.x 的应用程序,但最近它被用于 .NET Core 3.x Azure 函数.类库中没有任何变化,除了接受 sqlParameter,特别是 DbContext.Database.sqlQuery<T>()方法外,大多数方面似乎都按预期工作。

我遇到的问题似乎与 what happens when using EF Core with .NET Core 3.x without updating from System.Data.SqlClient to Microsoft.Data.SqlClient 非常相似,只是它颠倒了这个问题。异常消息是:

   The sqlParameterCollection only accepts non-null sqlParameter type objects,not sqlParameter objects.

但是,我遇到的所有文档都指出 EF 6 与 .NET Core 3.x 兼容,但 Microsoft.Data.sqlClient 兼容.我肯定在使用 System.Data.sqlClient.sqlParameter 并且我看不到应用程序在任何地方浸入 Microsoft.Data.sqlClient,如此部分堆栈跟踪所示:

   at System.Data.sqlClient.sqlParameterCollection.ValidateType(Object value)
   at System.Data.sqlClient.sqlParameterCollection.AddRange(Array values)
   at System.Data.Entity.Core.Objects.ObjectContext.CreateStoreCommand(String commandText,Object[] parameters)
   at System.Data.Entity.Core.Objects.ObjectContext.ExecuteStoreQueryInternal[TElement](String commandText,String entitySetName,Executionoptions executionoptions,Object[] parameters)
   at System.Data.Entity.Core.Objects.ObjectContext.<>c__displayClass186_0`1.<ExecuteStoreQueryReliably>b__1()
   at System.Data.Entity.Core.Objects.ObjectContext.ExecuteInTransaction[T](Func`1 func,IDbExecutionStrategy executionStrategy,Boolean startLocalTransaction,Boolean releaseConnectionOnSuccess)
   at System.Data.Entity.Core.Objects.ObjectContext.<>c__displayClass186_0`1.<ExecuteStoreQueryReliably>b__0()
   at System.Data.Entity.sqlServer.DefaultsqlExecutionStrategy.Execute[TResult](Func`1 operation)
   at System.Data.Entity.Core.Objects.ObjectContext.ExecuteStoreQueryReliably[TElement](String commandText,Object[] parameters)
   at System.Data.Entity.Core.Objects.ObjectContext.ExecuteStoreQuery[TElement](String commandText,Object[] parameters)
   at System.Data.Entity.Internal.InternalContext.<>c__displayClass111_0`1.<ExecutesqlQuery>b__0()
   at System.Data.Entity.Internal.LazyEnumerator`1.MoveNext()
   at System.Collections.Generic.List`1..ctor(IEnumerable`1 collection)
   at System.Linq.Enumerable.ToList[TSource](IEnumerable`1 source)
   <<a bunch of our custom stuff>>
   at Microsoft.Azure.WebJobs.Host.Executors.VoidMethodInvoker`2.InvokeAsync(TReflected instance,Object[] arguments) in C:\projects\azure-webjobs-sdk-rqm4t\src\Microsoft.Azure.WebJobs.Host\Executors\VoidMethodInvoker.cs:line 21
   at Microsoft.Azure.WebJobs.Host.Executors.FunctionInvoker`2.<InvokeAsync>d__10.MoveNext() in C:\projects\azure-webjobs-sdk-rqm4t\src\Microsoft.Azure.WebJobs.Host\Executors\FunctionInvoker.cs:line 52

编辑:这是解决方案中的精简代码...

在 .NetCore 3.1 函数 (v3) 中:

使用 Microsoft.Azure.ServiceBus; 使用 Microsoft.Azure.WebJobs; 使用 Microsoft.Extensions.Logging; 使用 MyProject.Services;

命名空间 MyProject.Functions { 公开课 MyFunction { 私有只读 MyDbContext _ctx;

    public MyFunction(MyDbContext ctx)
    {
        _ctx = ctx;
    }


    [FunctionName("MyFunction")]
    public override void Run([ServiceBusTrigger("%QueueName%",Connection = "%ConnectionString%")]
        Message msg,ILogger log)
    {
        var service = new MyService();

        service.DoStuff();
    }
}

}

在 .NET 4.8 类库中:

使用 System.Collections.Generic; 使用 System.Data.sqlClient; 使用 System.Linq;

命名空间 MyProject.Services { 公共类 MyService { 私有只读 MyDbContext _context;

    public MyService(MyDbContext ctx)
    {
        _context = ctx;
    }


    public void DoStuff()
    {
        //this works
        var lineItems1 = _context.LineItems.Where(li => li.Description == "something arbitrary").ToList();

        //this gives the exception and stack trace from the original post
        var lineItems2 = _context.Database.sqlQuery<LineItem>(
            "SELECT * FROM LineItems WHERE Description = @Description",new[] { new sqlParameter("@Description","something arbitrary") }).ToList();
    }
}

}

版权声明:本文内容由互联网用户自发贡献,该文观点与技术仅代表作者本人。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌侵权/违法违规的内容, 请发送邮件至 dio@foxmail.com 举报,一经查实,本站将立刻删除。