Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

How to share a connection string between multiple entity data model

I have a project that has 4 entity data model.for building them I don't want save a connection string in my project and I want store a connection string in app.config files and share it between my models.How I can do this?

thanks

like image 206
Arian Avatar asked Apr 22 '12 09:04

Arian


1 Answers

Assuming DbContext and model/database first.

  1. Leave the generated EF connection strings in your app.config file intact. As Arthur said, they contain the paths to the EF metadata (csdl/ssdl/msl). They are also used during development by the model designer.
  2. Add a store connection string called e.g. "SharedConnection". This is the only connection string which needs to be modified in production.
  3. Create a base class which derives from DbContext and derive all your contexts from that class.
  4. Create the default EF connection explicitely in the base class. Then modify it to use the shared connection string like that:
public class BaseContext : DbContext
{
    public BaseContext(string nameOrConnectionString)
        : base(CreateConnection(nameOrConnectionString), true)
    {
    }

    private static EntityConnection CreateConnection(string connectionString)
    {
        // Create a (plain old database) connection using the shared connection string.
        DbConnection dbConn = Database.DefaultConnectionFactory.CreateConnection(
            ConfigurationManager.ConnectionStrings["SharedConnection"].ConnectionString);

        // Create a helper EntityConnection object to build a MetadataWorkspace out of the
        // csdl/ssdl/msl parts of the generated EF connection string for this DbContext.
        EntityConnection wsBuilder = new EntityConnection(connectionString);

        // Merge the specific MetadataWorkspace and the shared DbConnection into a new EntityConnection.
        return new EntityConnection(wsBuilder.GetMetadataWorkspace(), dbConn);
    }
}

The code of the derived contexts does not change except that they must inherit from BaseContext. Here is a more robust CreateConnection method. It has error handling and removes the name of the shared connection string from the code at the price of adding an application setting.

private static EntityConnection CreateConnection(string connectionString)
{
    // Find the name of the shared connection string.
    const string appSettingKey = "SharedConnectionStringName";

    string sharedConnectionStringName = ConfigurationManager.AppSettings[appSettingKey];
    if (string.IsNullOrEmpty(sharedConnectionStringName))
    {
        throw new Exception(string.Format(
            "Shared connection not configured. " +
            "Please add a setting called \"{0}\" to the \"appSettings\" " +
            "section of the configuration file.", appSettingKey));
    }

    // Create a (plain old database) connection using the shared connection string.
    ConnectionStringSettings backendSettings =
        ConfigurationManager.ConnectionStrings[sharedConnectionStringName];
    if (backendSettings == null)
    {
        throw new Exception(string.Format(
            "Invalid connection string name \"{0}\" in appSetting \"{1}\"",
            sharedConnectionStringName, appSettingKey));
    }

    System.Data.Common.DbConnection dbConn =
        Database.DefaultConnectionFactory.CreateConnection(
        backendSettings.ConnectionString);

    // Create a helper EntityConnection object to build a MetadataWorkspace out of the
    // csdl/ssdl/msl parts of the generated EF connection string for this DbContext.
    EntityConnection wsBuilder = new EntityConnection(connectionString);

    // Merge the specific MetadataWorkspace and the shared DbConnection into a new EntityConnection.
    return new EntityConnection(wsBuilder.GetMetadataWorkspace(), dbConn);
}
like image 114
idilov Avatar answered Oct 26 '22 23:10

idilov