【问题标题】:Dynamic Connection String for EF Code FirstEF Code First 的动态连接字符串
【发布时间】:2018-10-04 01:02:15
【问题描述】:

我当前位于 Web.config 中的连接字符串是这样的:

  <add name="PersonDBContext" 
       connectionString="Server=111.111.1.11;
       Database=MyProgram;
       User Id=admin;
       Password=12345;
       Integrated Security=False" 
       providerName="System.Data.SqlClient" />

我想以动态的方式给程序提供相同的连接字符串,这是我的尝试:

    EntityConnectionStringBuilder csb = new EntityConnectionStringBuilder();

    csb.ProviderConnectionString = "Data Source=111.111.1.11;Initial Catalog=MyProgram;User Id=admin;Password=12345;Integrated Security=False";
    csb.Provider = "System.Data.SqlClient";

    String entityConnStr = csb.ToString();
    return entityConnStr;

这就是我得到的:

不支持关键字:'provider'。

你能告诉我我做错了什么吗? 我需要 Code First 连接字符串的元数据吗?谢谢。

编辑: 我认为我要么不应该使用 EntityConnectionStringBuilder,要么应该为 EntityConnectionStringBuilder 类提供元数据。你能告诉我如何做到这一点的方法之一吗?

【问题讨论】:

  • 我猜你正在使用访问数据库,对吧?
  • @sakir 我正在使用 SQL 数据库。

标签: c# entity-framework connection-string


【解决方案1】:

为什么不在 DbContext 派生类的构造函数中将其作为纯字符串传递? 喜欢

var ctx = new MyContext("Data Source=111.111.1.11;Initial Catalog=MyProgram;User Id=admin;Password=12345;Integrated Security=False");

【讨论】:

  • 因为这里没有指定提供者。
【解决方案2】:

为了让用户能够键入或选择他们想要连接的服务器,我必须做以下事情:

在 EF 创建的 Model.Context.cs 文件中,我将构造函数更改为:

public partial class Entities : DbContext
{
    public Entities()
        : base(BuildConnectionString)
    {
    }
    ...
}

然后我写了一个扩展类EntitiesEx.cs

partial class Entities : DbContext
{
    private static string BuildConnectionString 
    {
        get
        {
            // Specify the provider name, server and database.
            string providerName = "System.Data.SqlClient";
            string serverName = DatabaseController.Server;
            string databaseName = <DatabaseName>;

            // Initialize the connection string builder for the
            // underlying provider.
            SqlConnectionStringBuilder sqlBuilder = new SqlConnectionStringBuilder();

            // Set the properties for the data source.
            sqlBuilder.DataSource = serverName;
            sqlBuilder.InitialCatalog = databaseName;

            sqlBuilder.UserID = <user>;
            sqlBuilder.Password = <password>;

            sqlBuilder.IntegratedSecurity = false;

            sqlBuilder.PersistSecurityInfo = true;

            sqlBuilder.MultipleActiveResultSets = true;

            // Build the SqlConnection connection string.
            string providerString = sqlBuilder.ToString();

            // Initialize the EntityConnectionStringBuilder.
            EntityConnectionStringBuilder entityBuilder = new EntityConnectionStringBuilder();

            //Set the provider name.
            entityBuilder.Provider = providerName;

            // Set the provider-specific connection string.
            entityBuilder.ProviderConnectionString = providerString;

            //assembly full name
            Type t = typeof(Entities);
            string assemblyFullName = t.Assembly.FullName.ToString();

            // Set the Metadata location.
            entityBuilder.Metadata = string.Format("res://{0}/", //Models.Model.csdl|Models.Model.ssdl|Models.Model.msl", 
                assemblyFullName);

            try
            {
                //Test de conexion
                using (EntityConnection conn = new EntityConnection(entityBuilder.ToString()))
                {
                    conn.Open();

                    conn.Close();
                }
            }
            catch (Exception ex)
            {
                throw new Exception("Connection error" + ex.Message);
            }

            return entityBuilder.ToString();
        }
    }

作为一个缺点,每次从数据库生成模型时,都必须更改 Entities 类 (Model.Context.cs) 中的构造函数

【讨论】:

  • 由于 Model.Context.cs 被覆盖,您可以改为创建一个新文件,例如 Entities.cs。在public partial class Entities 中,由于已经定义了无参数构造函数,因此添加一个带有 1 个参数的构造函数。如果你要忽略这个参数,你可以从一个无参数的静态方法中调用构造函数。
【解决方案3】:

Code First 的动态连接字符串使用简单的 sql 连接字符串或不使用 EntityConnectionStringBuilder。所以你可以通过以下方式实现它。

public static string  DynamicConnectionString(SqlConnectionStringBuilder builder)
{
    SqlConnectionStringBuilder builder = new SqlConnectionStringBuilder();
    builder.DataSource = "ServerName";
    builder.InitialCatalog = "DatabaseName";
    builder.UserID = "UserId";
    builder.Password = "Password";
    builder.MultipleActiveResultSets = true;
    builder.PersistSecurityInfo = true;    
    return builder.ConnectionString.ToString();
}

【讨论】:

    【解决方案4】:

    原来是这样的:

    string entityConnStr = "Data Source=111.111.1.11;Initial Catalog=MyProgram;User Id=admin;Password=12345;Integrated Security=False";
    

    【讨论】:

    • 这将如何帮助连接其他数据库提供程序 MySql、MSQL 等。提供程序在哪里? @杰森
    • @NarendraSinghRathore 同意......我能找到的每个例子都是这样做的。如果是代码优先,他们会忽略提供者,如果他们包含提供者,则将其视为已建模。很高兴看到提供程序如何包含在代码优先示例中。
    猜你喜欢
    • 1970-01-01
    • 2023-04-09
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2011-10-24
    • 1970-01-01
    • 2012-09-04
    • 1970-01-01
    相关资源
    最近更新 更多