I'm Using Entity Framework 6 and I'm using migrations. I have already created the database using an initial migration. Now I have done changes to the Model and the context has changed, and I want to update the database BUT...
When I try to run again the Database-Update
command the seeds are also running too, and this bring errores due some data is inserted again.
Update-Database
command WITHOUT running the seed method?It is hard to believe that EF doesn't have any simple option like -No-Seed
for that. I'm almost secure that other ORMs does.
From the source code of DbMigrationsConfiguration<TContext>
:
/// <summary>
/// Runs after upgrading to the latest migration to allow seed data to be updated.
///
/// </summary>
///
/// <remarks>
/// Note that the database may already contain seed data when this method runs. This means that
/// implementations of this method must check whether or not seed data is present and/or up-to-date
/// and then only make changes if necessary and in a non-destructive way. The
/// <see cref="M:System.Data.Entity.Migrations.DbSetMigrationsExtensions.AddOrUpdate``1(System.Data.Entity.IDbSet{``0},``0[])"/>
/// can be used to help with this, but for seeding large amounts of data it may be necessary to do less
/// granular checks if performance is an issue.
/// If the <see cref="T:System.Data.Entity.MigrateDatabaseToLatestVersion`2"/> database
/// initializer is being used, then this method will be called each time that the initializer runs.
/// If one of the <see cref="T:System.Data.Entity.DropCreateDatabaseAlways`1"/>, <see cref="T:System.Data.Entity.DropCreateDatabaseIfModelChanges`1"/>,
/// or <see cref="T:System.Data.Entity.CreateDatabaseIfNotExists`1"/> initializers is being used, then this method will not be
/// called and the Seed method defined in the initializer should be used instead.
///
/// </remarks>
/// <param name="context">Context to be used for updating seed data. </param>
Basically, you don't have another option than implement an "add or update" logic because the Seed method will be executed each time after the initializer is used.
The AddOrUpdate extension method is useful for this, but I have also used this in some cases:
if (!context.Entities.Any())
{
// Seed
}
From this page:Database initializer and Migrations Seed methods:
The
Seed
method on theConfiguration
class runs whenever theUpdate-Database
PowerShell command is executed. Unless the Migrations initializer is being used the MigrationsSeed
method will not be executed when your application starts.
So, I think you don't have many options here, the migration Seed
method always will be called if you run Update-Database
command. I was digging if exist a parameter to this command that let you specify not run the Seed
method, but I'm fraid it don't exist yet. These are all the parameters you can use (you can find more info in this link):
Update-Database [-SourceMigration <String>] [-TargetMigration <String>] [-Script] [-Force]
[-ProjectName <String>] [-StartUpProjectName <String>] [-ConfigurationTypeName <String>]
[-ConnectionStringName <String>] [-AppDomainBaseDirectory <String>] [<CommonParameters>]
Update-Database [-SourceMigration <String>] [-TargetMigration <String>] [-Script] [-Force]
[-ProjectName <String>] [-StartUpProjectName <String>] [-ConfigurationTypeName <String>]
-ConnectionString <String> -ConnectionProviderName <String>
[-AppDomainBaseDirectory <String>] [<CommonParameters>]
If you are executing a sql script to insert data in the Seed
method, you could use a booleam condition to avoid reinsert the same fields after the first time.
As an aditional info, your request in have a parameter to avoid execute the Seed
method when you run the Update-Database
command already exist in this site, which is used by EF team to collect suggestions from the community.
I moved all my seed statements into separate methods that can be commented out easily before running 'update-database'.
protected override void Seed(Tpsc.EDI.EDIContext context)
{
try
{
//EDI.Seed.DoSeed(context);
}
catch (DbEntityValidationException e)
{
...
}
}
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With