31

¿Cuál es la mejor manera de ejecutar todas las migraciones de bases de datos requeridas al inicio de la aplicación con EF 4.3?Marco de entidades 4.3 ejecutar migraciones al inicio de la aplicación

+1

¿Quieres decir ejecutar desde el código? Entonces, aquí hay un enlace. Puede echar un vistazo http://romiller.com/2012/02/09/running-scripting-migrations-from-code/ –

Respuesta

50

La mejor manera debe ser utilizando el nuevo inicializador MigrateDatabaseToLatestVersion.

Database.SetInitializer<YourContext>(
    new MigrateDatabaseToLatestVersion<YourContext, YourMigrationsConfig>()); 
Database.Initialize(false); 
+4

¿Dónde se debe colocar este código? No se puede usar Database.Initialize en App_Start ya que no se puede usar en un contexto estático. –

+0

@ MaximV.Pavlov: intente agregarlo al constructor estático de su contexto. –

+0

@LadislavMrnka: ¿cuál es el propósito de 'Database.Initialize (false);'? Desde mi prueba con 'MigrateDatabaseToLatestVersion', la base de datos se crea, se inserta y se actualiza a la última versión sin esa segunda llamada a Initialize. (en EF5 ...) – demoncodemonkey

6

Una gran descripción de las opciones de configuración EF 4.3 se puede encontrar en EF 4.3 Configuration File Settings en el blog del equipo de ADO.NET. La última sección describe los inicializadores de base de datos, incluido el nuevo inicializador de Code First MigrateDatabaseToLatestVersion. Aunque Entity Framework -como muchas otras características de .NET 4.x- favorece la convención sobre la configuración, este es un caso donde podría ser muy útil establecer el inicializador de base de datos MigrateDatabaseToLatestVersion a través del archivo de configuración de la aplicación en lugar de código en tu aplicación.

+0

Al usar la configuración, también tome nota de mi comentario sobre esa publicación, para hacer que la configuración sea mucho más legible. – Rudi

4

Necesitaba hacerlo explícitamente, porque utilizo un uber-contexto para la migración, un superconjunto de las otras migraciones. El bit de clave es:

var dbMigrator = new System.Data.Entity.Migrations.DbMigrator(
    new Lcmp.EF.Migrations.Migrations.Configuration()); 
dbMigrator.Update(); 

con una rociada de la tala Elmah, en realidad yo uso este, llamado desde Application_Start(). Se roban fragmentos de las ideas de los demás. No estoy seguro de que la pieza enclavada de seguridad de hilo sea necesaria.

public static int IsMigrating = 0; 
private static void UpdateDatabase() 
{ 
    try 
    { 
     if (0 == System.Threading.Interlocked.Exchange(ref IsMigrating, 1)) 
     { 
      try 
      { 
       // Automatically migrate database to catch up. 
       Elmah.ErrorLog.GetDefault(null).Log(new Elmah.Error(new Exception("Checking db for pending migrations."))); 
       var dbMigrator = new System.Data.Entity.Migrations.DbMigrator(new Lcmp.EF.Migrations.Migrations.Configuration()); 
       var pendingMigrations = string.Join(", ", dbMigrator.GetPendingMigrations().ToArray()); 
       Elmah.ErrorLog.GetDefault(null).Log(new Elmah.Error(new Exception("The database needs these code updates: " + pendingMigrations))); 
       dbMigrator.Update(); 
       Elmah.ErrorLog.GetDefault(null).Log(new Elmah.Error(new Exception("Done upgrading database."))); 
      } 
      finally 
      { 
       System.Threading.Interlocked.Exchange(ref IsMigrating, 0); 
      } 
     } 
    } 
    catch (System.Data.Entity.Migrations.Infrastructure.AutomaticDataLossException ex) 
    { 
     Elmah.ErrorLog.GetDefault(null).Log(new Elmah.Error(ex)); 
    } 
    catch (Exception ex) 
    { 
     Elmah.ErrorLog.GetDefault(null).Log(new Elmah.Error(ex)); 
    } 
} 
Cuestiones relacionadas