Несколько контекстов БД в одной БД и приложении в EF 6 и первых миграциях кода

95

Я новичок в Entity Framework. Я пытаюсь настроить приложение MVC, использующее EF 6. Я использую Code First Migrations. Я использую области в приложении и хотел бы иметь разные DbContexts в каждой области, чтобы разбить ее. Я знаю, что в EF 6 есть ContextKey, но я не могу найти полную информацию о том, как его использовать. В настоящее время я могу использовать миграции только по одному контексту за раз.

Может ли кто-нибудь привести пример с достаточной детализацией, чтобы такой новый человек, как я, мог понять и использовать EF.

Lrayh
источник

Ответы:

177

Entity Framework 6 добавлена поддержка нескольких DbContextсекунд, добавляя -ContextTypeNameи -MigrationsDirectoryфлаги. Я просто запустил команды в консоли диспетчера пакетов и вставил результат ниже ...

Если у вас DbContextв проекте 2 секунды и вы запустите его enable-migrations, вы получите сообщение об ошибке (как вы, вероятно, уже знаете):

PM> enable-migrations
More than one context type was found in the assembly 'WebApplication3'.
To enable migrations for 'WebApplication3.Models.ApplicationDbContext', use Enable-Migrations -ContextTypeName WebApplication3.Models.ApplicationDbContext.
To enable migrations for 'WebApplication3.Models.AnotherDbContext', use Enable-Migrations -ContextTypeName WebApplication3.Models.AnotherDbContext.

Так что бегать придется enable-migrationsпо каждому DbContextотдельно. И вы должны указать папку для каждого Configuration.csсоздаваемого файла ...

PM> Enable-Migrations -ContextTypeName ApplicationDbContext -MigrationsDirectory Migrations\ApplicationDbContext
Checking if the context targets an existing database...
Code First Migrations enabled for project WebApplication3.

PM> Enable-Migrations -ContextTypeName AnotherDbContext -MigrationsDirectory Migrations\AnotherDbContext
Checking if the context targets an existing database...
Code First Migrations enabled for project WebApplication3.

Чтобы добавить миграции для каждого DbContext, вы делаете это следующим образом, указав полное имя Configurationкласса:

PM> Add-Migration -ConfigurationTypeName WebApplication3.Migrations.ApplicationDbContext.Configuration "InitialDatabaseCreation"
Scaffolding migration 'InitialDatabaseCreation'.
The Designer Code for this 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 in this migration, then you can re-scaffold it by running 'Add-Migration InitialDatabaseCreation' again.

PM> Add-Migration -ConfigurationTypeName WebApplication3.Migrations.AnotherDbContext.Configuration "InitialDatabaseCreation"
Scaffolding migration 'InitialDatabaseCreation'.
The Designer Code for this 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 in this migration, then you can re-scaffold it by running 'Add-Migration InitialDatabaseCreation' again.

И вы бежите так update-databaseже:

PM> Update-Database -ConfigurationTypeName WebApplication3.Migrations.ApplicationDbContext.Configuration
Specify the '-Verbose' flag to view the SQL statements being applied to the target database.
Applying explicit migrations: [201402032113124_InitialDatabaseCreation].
Applying explicit migration: 201402032113124_InitialDatabaseCreation.
Running Seed method.

PM> Update-Database -ConfigurationTypeName WebApplication3.Migrations.AnotherDbContext.Configuration
Specify the '-Verbose' flag to view the SQL statements being applied to the target database.
Applying explicit migrations: [201402032113383_InitialDatabaseCreation].
Applying explicit migration: 201402032113383_InitialDatabaseCreation.
Running Seed method.

Надеюсь это поможет.

Энтони Чу
источник
Должен ли я иметь отдельную строку подключения для каждого контекста или есть способ обойти это?
Lrayh 04
3
Они могут использовать одну и ту же строку подключения. Но вы хотите убедиться, что они не соответствуют одним и тем же таблицам.
Энтони Чу
Если они сопоставляются с одной и той же таблицей, вы все равно можете определить, какая миграция будет запущена первой, и оставить ее файл миграции для создания таблицы, а какой - второй, и изменить его так, чтобы он не создавал уже существующую таблицу. Затем вы можете использовать MigrateDatabaseToLatestVersionпринудительный запуск ctx.Database.initialize()каждого контекста в правильном порядке или запустить Update-Databaseкоманду вручную в правильном порядке. (И наоборот, если вы выполняете миграцию БД в предыдущую версию). Это «опасно», но можно.
JotaBe
Поэтому я добавил в свой проект миграции и создал контекст, отличный от ApplicationDbContext. Я продолжал использовать этот контекст, который был данными, относящимися к сайту, около 6 месяцев, затем пришло время начать возиться с моим ApplicationUser. Мой базовый вход в систему и регистрация работали, но я хотел расширить класс пользователя, добавив несколько дополнительных полей. Этот ответ был очень полезен при настройке новой конфигурации миграции для этого контекста. Спасибо! # 1up
Эрик Бишард
1
если я могу дать вам +10 за этот короткий, но более чем достаточный ответ, я бы хотел, спасибо @AnthonyChu.
Karim AG