views:

98

answers:

1

In LinqToSql I could write an empty constructor if I set the Connection string to (None). In that empty constructor I could then pull the connection string from the web.Config like so:

    public CustomDataDataContext() :
  base( ConfigurationManager.ConnectionStrings[ "DB" ].ConnectionString, mappingSource )
{
  OnCreated();
}

I am trying to do the same thing now in Entity Framework 4.0. Is this possible somehow? I can't seem to get rid of their generated paramaterless constructor. I would rather not wrap the context in a new class that feeds the context the connection string to the context if I do not have to.

+3  A: 

While a parameterless constructor which automatically finds a connection seems like a good idea, it tightly couples the object context to the configuration file.

It also introduces some "magic" in that the consumer has no clear way to determine how to change the connection string associated with the parameterless constructor (except to read the source).

I guess my answer is, regardless of whether the Entity Framework allows you to do this, you probably shouldn't. Use a factory instead, and achieve the same flexibility without tying the object context to the configuration system:

public interface ICustomDataContextFactory
{
    CustomDataContext Create();
}

public class CustomDataContextFactory : ICustomDataContextFactory
{
    private readonly string _connectionStringName;

    public CustomDataContextFactory(string connectionStringName)
    {
        _connectionStringName = connectionStringName;
    }

    public CustomDataContext Create()
    {
        var connectionString = ConfigurationManager.ConnectionStrings[_connectionStringName].ConnectionString;

        return new CustomDataContext(connectionString);
    }
}

This provides all consumers the same mechanism for creating a parameterless instance, while allowing implementors to decide how the instance is created - perhaps a different connection string needs to be used for a particular instance, or the database name is read from the command line on startup.

I realize that you said you don't want to introduce a new class which passes the connection string through. I took that to mean a class derived from CustomDataContext and not a factory, which is a new concept here.

(This answer only really applies to production code. The parameterless constructor trick is useful in ephemeral code like proofs-of-concept.)

Bryan Watts