Как и где вызывать Database.EnsureCreated и Database.Migrate?

У меня есть приложение ASP.NET MVC 6, и мне нужно вызвать методы Database.EnsureCreated и Database.Migrate.

Но куда мне их звать?

Ответы

Ответ 1

Я думаю, что это важный вопрос, и на него нужно дать хороший ответ!

Что такое Database.EnsureCreated?

context.Database.EnsureCreated() - это новый основной метод EF, который обеспечивает существование базы данных для контекста. Если он существует, никаких действий не предпринимается. Если он не существует, то создается база данных и вся ее схема, а также она обеспечивает совместимость с моделью для этого контекста.

Примечание. Этот метод не использует миграции для создания базы данных. Кроме того, созданная база данных не может быть позже обновлена с помощью миграций. Если вы ориентируетесь на реляционную базу данных и используете миграции, вы можете использовать метод DbContext.Database.Migrate() чтобы убедиться, что база данных создана и все миграции применены.

Как мы это сделали с EF 6?

context.Database.EnsureCreated() эквивалентен перечисленным ниже подходам EF 6:

  1. Консоль диспетчера пакетов:

    Включение-миграция -EnableAutomaticMigrations. Add-Migration/Update-Database.

  2. Из кода:

    Database.SetInitializer CreateDatabaseIfNotExists

или же

С помощью DbMigrationsConfiguration и установите AutomaticMigrationsEnabled = true;

Что такое Database.Migrate?

Применяет любые ожидающие миграции для контекста к базе данных. Создаст базу данных, если она еще не существует.

Как мы это сделали с EF 6?

context.Database.Migrate() эквивалентен перечисленным ниже подходам EF 6:

  1. Консоль диспетчера пакетов:

    Обновление базы данных -TargetMigration

  2. С пользовательской конфигурацией DbMigrationsConfiguration:

    AutomaticMigrationsEnabled = false; или с DbMigrator.

Вывод:

Если вы используете миграции, есть context.Database.Migrate(). Если вы не хотите миграций и просто хотите быструю базу данных (обычно для тестирования), используйте context.Database.EnsureCreated()/EnsureDeleted().

Ответ 2

С информацией, которую предоставили Джеймс П и Бассам Алугили, я закончил тем, что добавил следующие строки кода в метод Configure класса Startup (Startup.cs):

using (var scope = 
  app.ApplicationServices.GetRequiredService<IServiceScopeFactory>().CreateScope())
using (var context = scope.ServiceProvider.GetService<MyDbContext>())
    context.Database.Migrate();

Ответ 3

Так же, как вперед, вы должны прочитать это от Роуэн Миллер:

... EnsureCreated полностью обходит миграции и просто создает схему для вас, вы не можете смешивать это с миграциями. EnsureCreated предназначен для тестирования или быстрого прототипирования, когда вы можете каждый раз EnsureCreated и заново создавать базу данных. Если вы используете миграции и хотите, чтобы они автоматически применялись при запуске приложения, вы можете использовать context.Database.Migrate().

Согласно ответу здесь необходимо добавить Globals.EnsureDatabaseCreated(); это в Startup.cs:

Функция запуска в Startup.cs:

public Startup(IHostingEnvironment env)
{
    // Set up configuration sources.
    var builder = new ConfigurationBuilder()
            .AddJsonFile("appsettings.json")
            .AddEnvironmentVariables();

    if (env.IsDevelopment())
    {
        // This will push telemetry data through Application Insights pipeline faster, allowing you to view results immediately.
            builder.AddApplicationInsightsSettings(developerMode: true);
    }
    Configuration = builder.Build();
    Globals.Configuration = Configuration;
    Globals.HostingEnvironment = env;
    Globals.EnsureDatabaseCreated();
}

И определите Globals.EnsureDatabaseCreated() следующим образом:

public static void EnsureDatabaseCreated()
    {
        var optionsBuilder = new DbContextOptionsBuilder();
        if (HostingEnvironment.IsDevelopment()) optionsBuilder.UseSqlServer(Configuration["Data:dev:DataContext"]);
        else if (HostingEnvironment.IsStaging()) optionsBuilder.UseSqlServer(Configuration["Data:staging:DataContext"]);
        else if (HostingEnvironment.IsProduction()) optionsBuilder.UseSqlServer(Configuration["Data:live:DataContext"]);
        var context = new ApplicationContext(optionsBuilder.Options);
        context.Database.EnsureCreated();

        optionsBuilder = new DbContextOptionsBuilder();
        if (HostingEnvironment.IsDevelopment()) optionsBuilder.UseSqlServer(Configuration["Data:dev:TransientContext"]);
        else if (HostingEnvironment.IsStaging()) optionsBuilder.UseSqlServer(Configuration["Data:staging:TransientContext"]);
        else if (HostingEnvironment.IsProduction()) optionsBuilder.UseSqlServer(Configuration["Data:live:TransientContext"]);
        new TransientContext(optionsBuilder.Options).Database.EnsureCreated();
    }

Для использования context.Database.Migrate() смотрите здесь или здесь.

Ответ 4

Кроме того, вы можете увидеть EnsureCreated производительности, если вызовите это в конструкторе вашего контекста... После перемещения EnsureCreated в утилиту setup.cs я заметил значительное улучшение времени отклика.

Примечание: я использую EFC и UWP.