如何在Azure函数中指定EntityFramework ProviderName [英] How to specify EntityFramework ProviderName in an Azure Function

查看:331
本文介绍了如何在Azure函数中指定EntityFramework ProviderName的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我试图将一些webjob代码移植到新的Azure函数中。到目前为止,我设法导入我的DLL并成功引用它们,但是当我在代码中使用连接字符串时,出现错误,提示我必须添加ProviderName:


应用程序的
配置文件中的连接字符串'ConnectionString'不包含必需的providerName
属性。


这通常不会成为问题,因为在webjob(或web应用程序)中,这将位于App或Web.config中,而连接字符串将被我随便输入的内容Azure。



使用Azure函数,我没有web.config(尽管我尝试添加一个无效),所以很自然地缺少了providername。



如何指定?

编辑:
周围和一些有用的提示,我几乎设法得到它的工作。



我现在所做的是ing:

  var connString = **来自配置的MY CONN STRING **; //没有元数据的Constring 
EntityConnectionStringBuilder b = new EntityConnectionStringBuilder();
b.Metadata =res://*/Entities.MyDB.csdl | res://*/Entities.MyDB.ssdl | res://*/Entities.MyDB.msl;
b.ProviderConnectionString = connString.ConnectionString;
b.Provider =System.Data.SqlClient;
返回新的MyDB(b.ConnectionString);

这给了我调用数据库所需的东西。我在部分类中使用静态方法来获取运行上述代码的数据库实例,并使用 [DbConfigurationType(typeof(MyDbConfiguration))]



我将该配置定义为:

  public class MyDBConfiguration: DbConfiguration 
{
public MyDBConfiguration()
{
SetProviderFactory(System.Data.EntityClient,EntityProviderFactory.Instance);
}
}

我的问题仍然存在我想实际使用EF实体。在这里,它将尝试使用原始配置初始化数据库类型,并再次给我原始错误。根据这个堆栈跟踪:

  at Void Initialize()
at System.Data.Entity.Internal.EntitySetTypePair GetEntitySetAndBaseTypeForType (System.Type)
at Void InitializeContext()
at System.Data.Entity.Core.Objects.ObjectContext CreateObjectContextFromConnectionModel()
at Void Initialize()
at Boolean TryInitializeFromAppConfig( System.String,System.Data.Entity.Internal.AppConfig)
at Void InitializeFromConnectionStringSetting(System.Configuration.ConnectionStringSettings)

所以我该如何避免这种情况?我想我需要一种方法来钩住一切并运行我的自定义设置器。

解决方案

最后,斯蒂芬Reindel把我推向了正确的方向;实体框架的基于代码的配置。

pre $ [code] [DbConfigurationType(typeof(MyDBConfiguration))]
public partial class MyDB
{
public static MyDB GetDB()
{
var connString = ** MY CONNECT STRING FROM SOMEWHERE **; //没有元数据的Constring
EntityConnectionStringBuilder b = new EntityConnectionStringBuilder();
b.Metadata =res://*/Entities.MyDB.csdl | res://*/Entities.MyDB.ssdl | res://*/Entities.MyDB.msl;
b.ProviderConnectionString = connString.ConnectionString;
b.Provider =System.Data.SqlClient;
返回新的MyDB(b.ConnectionString);

$ b $ public MyDB(string connectionString):base(connectionString)
{
}
}



使用这样的MyDbConfiguration:

  public class MyDBConfiguration :DbConfiguration 
{
public MyDBConfiguration()
{
SetProviderServices(System.Data.SqlClient,SqlProviderServices.Instance);
SetDefaultConnectionFactory(new SqlConnectionFactory());




$ b $ p
$ b

通过上面的代码,EF从不要求AppConfig-相关的配置文件。但记住,如果您的配置文件中有EF条目,它会尝试使用它们,因此请确保它们已经不存在。



就azure函数而言,这意味着我使用Azure中的Azure函数配置面板在没有元数据和提供程序名称的情况下插入ConnectionString,然后将其加载到GetDB中。



编辑:根据请求,以下是上述说明文字: b $ b您无法添加有关Azure函数中连接的EF元数据,因为它们的确如此不要使用app.config来指定它。这不是连接字符串的一部分,而是除了EF用于映射到特定C#类和SQL提供程序等的连接字符串之外的有关连接的元数据。为避免此问题,请使用上述示例对其进行硬编码。你可以通过创建一个继承自DBConfiguration的类来实现这一点,然后用这个类标记(用一个部分类的属性)EF数据库类。实例化一个新的数据库对象的方式,其中这个元数据是硬编码的,但连接字符串是从Azure中的应用程序设置中检索的。在这个例子中,我只是使用了一个静态方法,但我想它也可能是一个新的构造函数。



一旦你使用了这个静态方法,你可以用它来使用(var db = MyDB.GetDB()){
//数据库代码在这里。


$


这允许你在没有APP.Config的情况下使用EntityFramework,而且你仍然可以使用Azure功能APP设置更改连接字符串。



希望有帮助


I'm trying to port some webjob code to the new Azure Functions. So far I've managed to import my DLL's and reference them succesfully, but when I use the connection string in my code, I get an error saying I have to add the ProviderName:

The connection string 'ConnectionString' in the application's configuration file does not contain the required providerName attribute."

Which is normally not a problem because in a webjob (or web app), this will be in the App or Web.config, and the connectionstring will simply be overwritten with whatever I entered in Azure.

With Azure Functions, I don't have a web.config (Although I tried adding one to no avail), so naturally the providername is missing.

How do I specify that?

EDIT: After some playing around and some helpful tips by people below, I've almost managed to get it working.

What I do now is the following:

    var connString = **MY CONN STRING FROM CONFIG**; // Constring without metadata etc.
    EntityConnectionStringBuilder b = new EntityConnectionStringBuilder();
    b.Metadata = "res://*/Entities.MyDB.csdl|res://*/Entities.MyDB.ssdl|res://*/Entities.MyDB.msl";
    b.ProviderConnectionString = connString.ConnectionString;
    b.Provider = "System.Data.SqlClient";
    return new MyDB(b.ConnectionString);

Which gives me what I need for calling the database. I use a static method in a partial class to get an instance of the Database which runs the above code, and I decorate my MyDB Partial with [DbConfigurationType(typeof(MyDbConfiguration))]

I define that configuration as:

public class MyDBConfiguration: DbConfiguration
{
    public MyDBConfiguration()
    {
        SetProviderFactory("System.Data.EntityClient", EntityProviderFactory.Instance);
    }
}

My problem remains when I want to actually use the EF Entities. Here, it will try to initialize the database type using the original configuration, giving me the original error once again. As per this stack trace:

at Void Initialize()
at System.Data.Entity.Internal.EntitySetTypePair GetEntitySetAndBaseTypeForType(System.Type)
at Void InitializeContext()
at System.Data.Entity.Core.Objects.ObjectContext CreateObjectContextFromConnectionModel()
at Void Initialize()
at Boolean TryInitializeFromAppConfig(System.String, System.Data.Entity.Internal.AppConfig)
at Void InitializeFromConnectionStringSetting(System.Configuration.ConnectionStringSettings)

So how do I avoid this? I guess I need a way to hook into everything and run my custom setter..

解决方案

In the end, Stephen Reindel pushed me in the right direction; Code-based Configuration for Entity Framework.

[DbConfigurationType(typeof(MyDBConfiguration))]
public partial class MyDB
{
   public static MyDB GetDB()
   {
      var connString = **MY CONN STRING FROM SOMEWHERE**; // Constring without metadata etc.
      EntityConnectionStringBuilder b = new EntityConnectionStringBuilder();
      b.Metadata = "res://*/Entities.MyDB.csdl|res://*/Entities.MyDB.ssdl|res://*/Entities.MyDB.msl";
      b.ProviderConnectionString = connString.ConnectionString;
      b.Provider = "System.Data.SqlClient";
      return new MyDB(b.ConnectionString);
   }

   public MyDB(string connectionString) : base(connectionString)
   {
   }
}

With MyDbConfiguration like this:

public class MyDBConfiguration: DbConfiguration
{
    public MyDBConfiguration()
    {
        SetProviderServices("System.Data.SqlClient", SqlProviderServices.Instance);
        SetDefaultConnectionFactory(new SqlConnectionFactory());
    }
}

With the above code, EF never asks for AppConfig-related config files. But remember, if you have EF entries in your config file, it will attempt to use them, so make sure they're gone.

In terms of azure functions, this means I used the Azure Functions configuration panel in azure to punch in my ConnectionString without the Metadata and providername, and then loaded that in GetDB.

Edit: As per request, here is some explanatory text of the above: You can't add EF metadata about the connection in Azure Functions, as they do not use an app.config in which to specify it. This is not a part of the connection string, but is metadata about the connection besides the connection string that EF uses to map to a specific C# Class and SQL Provider etc. To avoid this, you hardcode it using the above example. You do that by creating a class inheriting from DBConfiguration, and you mark (with an attribute on a partial class) your EF database class with that.

This DBConfiguration contains a different kind of way to instantiate a new database object, in which this metadata is hardcoded, but the connectionstring is retrieved from your app settings in Azure. In this example I just used a static method, but I guess it could be a new constructor also.

Once you have this static method in play, you can use that to get a new database in your database code, like this:

using (var db = MyDB.GetDB()) {
   // db code here.
}

This allows you to use EntityFramework without an APP.Config, and you can still change the connectionstring using Azure Functions APP settings.

Hope that helps

这篇关于如何在Azure函数中指定EntityFramework ProviderName的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆