10
votes

In most asp.net applications you can change the database store by modifing the connectionstring at runtime. i.e I can change from using a test database to a production database by simply changing the value of the "database" field in the connectionstring

I'm trying to change the schema (but not necessarily the database itself) with entity framework but no luck.

The problem I'm seeing is the that the SSDL content in the edmx xml file is storing the schema for each entityset.

see below

<EntitySet 
    Name="task" 
    EntityType="hardModel.Store.task" 
    store:Type="Tables" 
    Schema="test"  />

Now I have changed the schema attribute value to "prod" from test and it works..

But this does not seem to be a good solution.

  1. I need to update evert entity set as well as stored procedures ( I have +50 tables )
  2. I can only do this an compile time?
  3. If I then try to later update the Entity model-entityies that already exist are being read due to EF not recognizing that the table already exists in the edm.

Any thoughts?

8
To be clear I do have prod and test on different server. The actual situation is that I want to run from ONE machine using ONE instance of MySQL 2 versions of my app. Each version should run on a separate 'schema'/database. EF is storing the schema name as part of the EF ssdl file and using this design time schema to generate SQL queries which will fail since the schema is not guranteed to be named the same related - stackoverflow.com/questions/1307083/… - user48545

8 Answers

2
votes

Update Upon reading your comments it's clear that you're wanting to change the referenced schema for each DB, not the database. I've edited the question to clarify this and to restore the sample EDMX you provided which was hidden in the original formatting.

I'll repeat my comment below here:

If the schemata are in the same DB, you can't switch these at runtime (except with EF 4 code-only). This is because two identically-named and structured tables in two different schemata are considered entirely different tables.

I also agree with JMarsch above: I'd reconsider the design of putting test and production data (or, actually, 'anything and production data') in the same DB. Seems like an invitation to disaster.

Old answer below.

Are you sure you're changing the correct connection string? The connection string used by the EF is embedded inside the connection string which specifies the location of CSDL/SSDL/etc. It's common to have a "normal" connection string for use by some other part of your app (e.g., ASP.NET membership). In this case, when changing DBs you must update both of your connection strings.

Similarly, if you update the connection string at runtime then you must use specific tools for this, which understand the EF connection string format and are separate from the usual connection string builder. See the example in the link. See also this help on assigning EF connection strings.

6
votes

I have this same issue and it's really rather annoying, because it's one of those cases where Microsoft really missed the boat. Half the reason to use EF is support for additional databases, but unless you go code first which doesn't really address the problem.

In MS SQL changing the schema makes very little sense, because the schema is part of the identity of the tables. For other types of databases, the schema is very much not part of the identity of the database and only determines the location of the database. Connect to Oracle and changing the database and changing the schema are essentially synonymous.

2
votes

The easiest way to solve the problem is to manualy remove all entries like 'Schema="SchemaName"' from the SSDL part of the model.
Everything works propely in this case.

2
votes

Sorry its not a robust answer but I found this project on codeplex ( as well as this question ) while googling around for a similar problem:

http://efmodeladapter.codeplex.com/

The features include:

  • Run-time adjustment of model schema, including:
  • Adjusting data-level table prefixes or suffixes
  • Adjusting the owner of database objects

Some code from the docs:

public partial class MyObjectContext : BrandonHaynes.ModelAdapter.EntityFramework.AdaptingObjectContext
{
        public MyObjectContext() 
        : base(myConnectionString, 
        new ConnectionAdapter(
            new TablePrefixModelAdapter("Prefix", 
                new TableSuffixModelAdapter("Suffix")), 
        System.Reflection.Assembly.GetCallingAssembly()))
    {
    ...
    }

}

Looks like its exactly what your looking for.

1
votes

The connection string for EF is in the config file. There is no need to change the SSDL file.

EDIT

Do you have the prod and test schema in the same database?

If Yes you can fix it by using a seperate database for prod and test. Using the same schema name in both databases.

If No you can fix it by Using the same schema name in both databases.

If you will absolutly have different schema names, create two EF models, one for test and one for prod, then select which on to use in code based on a value in your config file.

1
votes

When I create a new "ADO.NET Entity Data Model", there are two properties "Entity Container Name" and "Namespace" available for editing in design view.. Using the namespace.EntityContainerName, you can create a new instance specifying a connection string.

MyEntities e = new MyEntities("connstr");
e.MyTable.Count();

I'm not sure if this helps you or not, good luck!

Also, this is a good case for multiple layers (doesn't have to be projects, but could be).

Solution
* DataAccess - Entities here
* Service - Wraps access to DataAccess
* Consumer - Calls Service

In this scenario, the consumer calls service, passing in whatever factor determines which connection string is used. The service then instantiates an instance of data access passing in the appropriate connection string and executes the consumer's query.

1
votes

Here is a similar question with a better answer: Changing schema name on runtime - Entity Framework

The solution that worked for me was the one written by Jan Matousek.

0
votes

Solved my problem by moving to sql server and away from mysql.

Mysql and Mssql interpret "schemas" differently. Schemas in mysql are the same/synonyms to databases. When I created the model the schema name..which is the same as the database name is hard coded in the generated model xml. In Mssql the schema is by default "dbo" which gets hard coded but this isnt an issue since in mssql schemas and databases are different.