Tips When Making Changes in Entity Framework Code First Models after Scaffolding

When you scaffold an existing Entity Framework model, using MVC5 scaffolding in Visual Studio 2013, you can easily run into the issue of “The model backing the <DbContextName> context has changed since the database was created” as shown below.

Scaffold the Product model again and view a scaffold page, you will see the error message mentioned above. The exception is caused by the model change, not actually a scaffolding issue. However, because of the order in which users do things, it might sometimes appear to be related to scaffolding.

There are a few ways to workaround this error; each has some pros and cons, depending on what you need.

1) Code First Migration with Entity Framework.

First, you need to bring up “Package Manager Console”, Tools –> Library Package Manger –> Package Manager Console, and run the Enable-Migrations command in the console as the first step to enable migrations for your context.

Detected database created with a database initializer. Scaffolded migration '201309271941079_InitialCreate' corresponding to existing database. To use an automatic migration instead, delete the Migrations folder and re-run Enable-Migrations specifying the -EnableAutomaticMigrations parameter.

Code First Migrations enabled for project WebApplication7.

From now on, each time you modify the model and re-run the scaffolding, you need to run the Add-Migration, and Update-Database commands. In our example above, after adding Description and Category, we run those commands as follows.

PM> Add-Migration AddDescriptionCategory

Scaffolding migration 'AddDescriptionCategory'.

The Designer Code forthis migration file includes a snapshot of your current Code First model. This snapshot is used to calculate the changes to your model when you scaffold the next migration. If you make additional changes to your model that you want to include inthis migration, then you can re-scaffold it by running 'Add-Migration AddDescriptionCategory' again.

PM> Update-Database

Specify the '-Verbose' flag to view the SQL statements being applied to the target database.

Now you can test view the scaffolded pages and won’t see the error anymore.

The good thing about this approach is you just modify the exact table representing the model that you’re changing, and leave the rest of the database intact. However, if you do a lot of changes on the model and want some quick verification of the scaffold pages, going through those steps each time can add a considerable amount of time. Also, those steps will add a number of files into your projects that can grow quickly.

2) Modify the Database name in the connectionString

A quick workaround to the existing database issue without going through all the database migration steps would be to modify the connection string in web.config. Each time you change the code first model and scaffold it, you can give the connection string a new “Initial Catalog” and “AttachDbFilename” value.

This approach will create a new database each time you give a new database name in the connection string and leave the old database unused. This might not be ideal if you already have a large existing database. However, it could be useful if you just want to verify something quick once or twice.

3) Database Initializer with Entity Framework

With the second workaround, you still need to remember to modify the connection string each time the model is changed. If you want to make one setting, and forget about it when you’re building your app, you can achieve this with a custom initializer class. EF will drop, recreate and re-seed the database each time the model changes, and you set up this action only once in your project.

From now on, you can just focus on building the right model for your application, scaffold, and test it as many times as you need, and don’t have to do anything extra in order to avoid the error mentioned at the beginning of this blog.

This approach will drop and create a new database only when the model is changed, and it won’t leave behind a lot of unused databases, which option 2 will do.

Another way to tell Entity Framework to use your initializer class is to add an element to the entityFramework element in the application’s Web.config file, instead of modifying the Global.asax.cs file. For more information about how to do it, you can read Tom’s fabulous blog at Creating an Entity Framework Data Model for an ASP.NET MVC Application. Setting up the initializer in the Web.Config file is sometimes preferable because you can turn it on or off or change it without changing code.