Stosowanie migracji
Po dodaniu migracji należy je wdrożyć i zastosować do baz danych. Istnieją różne strategie tego działania, a niektóre są bardziej odpowiednie dla środowisk produkcyjnych, a inne dla cyklu projektowania.
Uwaga
Niezależnie od strategii wdrażania zawsze sprawdzaj wygenerowane migracje i przetestuj je przed zastosowaniem do produkcyjnej bazy danych. Migracja może spowodować usunięcie kolumny, gdy intencja miała ją zmienić lub może zakończyć się niepowodzeniem z różnych powodów, gdy zastosowano ją do bazy danych.
Skrypty SQL
Zalecanym sposobem wdrażania migracji do produkcyjnej bazy danych jest generowanie skryptów SQL. Zalety tej strategii obejmują następujące elementy:
- Skrypty SQL można przeglądać pod kątem dokładności; Jest to ważne, ponieważ stosowanie zmian schematu w produkcyjnych bazach danych jest potencjalnie niebezpieczną operacją, która może obejmować utratę danych.
- W niektórych przypadkach skrypty można dostosować do określonych potrzeb produkcyjnej bazy danych.
- Skrypty SQL mogą być używane w połączeniu z technologią wdrażania, a nawet mogą być generowane w ramach procesu ciągłej integracji.
- Skrypty SQL mogą być udostępniane administratorowi bazy danych i mogą być zarządzane i archiwizowane oddzielnie.
Podstawowy sposób użycia
Następujące polecenie generuje skrypt SQL z pustej bazy danych do najnowszej migracji:
dotnet ef migrations script
Z od (do implikowane)
Poniższy kod generuje skrypt SQL z danej migracji do najnowszej migracji.
dotnet ef migrations script AddNewTables
Z i do
Poniższe polecenie generuje skrypt SQL z określonej from
migracji do określonej to
migracji.
dotnet ef migrations script AddNewTables AddAuditTable
Możesz użyć elementu from
nowszego to
niż w celu wygenerowania skryptu wycofywania.
Ostrzeżenie
Zanotuj potencjalne scenariusze utraty danych.
Generowanie skryptu akceptuje następujące dwa argumenty, aby wskazać, który zakres migracji należy wygenerować:
- Migracja z migracji powinna być ostatnią migracją zastosowaną do bazy danych przed uruchomieniem skryptu. Jeśli nie zastosowano żadnych migracji, określ
0
wartość (jest to ustawienie domyślne). - Migracja to ostatnia migracja, która zostanie zastosowana do bazy danych po uruchomieniu skryptu. Ta wartość domyślna to ostatnia migracja w projekcie.
Idempotentne skrypty SQL
Skrypty SQL wygenerowane powyżej można zastosować tylko w celu zmiany schematu z jednej migracji na inną; Użytkownik jest odpowiedzialny za odpowiednie zastosowanie skryptu i tylko do baz danych w prawidłowym stanie migracji. Program EF Core obsługuje również generowanie skryptów idempotentnych , które wewnętrznie sprawdzają, które migracje zostały już zastosowane (za pośrednictwem tabeli historii migracji) i stosują tylko brakujące. Jest to przydatne, jeśli nie wiesz dokładnie, jaka była ostatnia migracja zastosowana do bazy danych, lub jeśli wdrażasz w wielu bazach danych, które mogą znajdować się w innej migracji.
Następujące elementy generują migracje idempotentne:
dotnet ef migrations script --idempotent
Narzędzia wiersza polecenia
Narzędzia wiersza polecenia ef mogą służyć do stosowania migracji do bazy danych. Chociaż produktywne w przypadku lokalnego tworzenia i testowania migracji, takie podejście nie jest idealne do zarządzania produkcyjnymi bazami danych:
- Polecenia SQL są stosowane bezpośrednio przez narzędzie bez możliwości sprawdzenia lub zmodyfikowania ich przez dewelopera. Może to być niebezpieczne w środowisku produkcyjnym.
- Zestaw .NET SDK i narzędzie EF muszą być zainstalowane na serwerach produkcyjnych i wymagają kodu źródłowego projektu.
Następujące aktualizacje bazy danych do najnowszej migracji:
dotnet ef database update
Następujące aktualizacje bazy danych do danej migracji:
dotnet ef database update AddNewTables
Należy pamiętać, że można go również użyć do wycofania do wcześniejszej migracji.
Ostrzeżenie
Zanotuj potencjalne scenariusze utraty danych.
Aby uzyskać więcej informacji na temat stosowania migracji za pomocą narzędzi wiersza polecenia, zobacz dokumentację narzędzi platformy EF Core.
Pakiety
Pakiety migracji to pliki wykonywalne z jednym plikiem, których można użyć do stosowania migracji do bazy danych. Dotyczą one niektórych niedociągnięć skryptu SQL i narzędzi wiersza polecenia:
- Wykonywanie skryptów SQL wymaga dodatkowych narzędzi.
- Obsługa transakcji i dalsze zachowanie tych narzędzi są niespójne i czasami nieoczekiwane. Może to pozostawić bazę danych w stanie niezdefiniowanym, jeśli wystąpi błąd podczas stosowania migracji.
- Pakiety można wygenerować w ramach procesu ciągłej integracji i łatwo wykonać później w ramach procesu wdrażania.
- Pakiety można wykonywać bez instalowania zestawu .NET SDK lub narzędzia EF (a nawet środowiska uruchomieniowego platformy .NET, gdy są one samodzielne) i nie wymagają kodu źródłowego projektu.
Następujące elementy generują pakiet:
dotnet ef migrations bundle
Następujące elementy generują samodzielny pakiet dla systemu Linux:
dotnet ef migrations bundle --self-contained -r linux-x64
Aby uzyskać więcej informacji na temat tworzenia pakietów, zobacz dokumentację narzędzi EF Core.
efbundle
Wynikowy plik wykonywalny jest domyślnie nazwany efbundle
. Może służyć do aktualizowania bazy danych do najnowszej migracji. Jest to odpowiednik uruchamiania dotnet ef database update
lub Update-Database
.
Argumenty:
Argument | opis |
---|---|
<MIGRATION> |
Migracja docelowa. Jeśli wartość "0", wszystkie migracje zostaną przywrócone. Domyślnie jest to ostatnia migracja. |
Opcje:
Opcja | Krótkie | opis |
---|---|---|
--connection <CONNECTION> |
Parametry połączenia do bazy danych. Wartość domyślna to określona w elemecie AddDbContext lub OnConfiguring. | |
--verbose |
-v |
Pokaż pełne dane wyjściowe. |
--no-color |
Nie koloruj danych wyjściowych. | |
--prefix-output |
Prefiks danych wyjściowych z poziomem. |
Poniższy przykład dotyczy migracji do lokalnego wystąpienia programu SQL Server przy użyciu określonej nazwy użytkownika i poświadczeń:
.\efbundle.exe --connection 'Data Source=(local)\MSSQLSERVER;Initial Catalog=Blogging;User ID=myUsername;Password={;'$Credential;'here'}'
Ostrzeżenie
Nie zapomnij skopiować appsettings.json obok pakietu. Pakiet opiera się na obecności appsettings.json w katalogu wykonywania.
Przykład pakietu migracji
Pakiet wymaga, aby uwzględnić migracje. Są one tworzone przy użyciu zgodnie z dotnet ef migrations add
opisem w temacie Tworzenie pierwszej migracji. Po zakończeniu migracji do wdrożenia utwórz pakiet przy użyciu narzędzia dotnet ef migrations bundle
. Na przykład:
PS C:\local\AllTogetherNow\SixOh> dotnet ef migrations bundle
Build started...
Build succeeded.
Building bundle...
Done. Migrations Bundle: C:\local\AllTogetherNow\SixOh\efbundle.exe
PS C:\local\AllTogetherNow\SixOh>
Dane wyjściowe są plikiem wykonywalnym odpowiednim dla docelowego systemu operacyjnego. W moim przypadku jest to system Windows x64, więc otrzymuję porzucony efbundle.exe
w moim folderze lokalnym. Uruchomienie tego pliku wykonywalnego powoduje zastosowanie zawartych w nim migracji:
PS C:\local\AllTogetherNow\SixOh> .\efbundle.exe
Applying migration '20210903083845_MyMigration'.
Done.
PS C:\local\AllTogetherNow\SixOh>
Podobnie jak w przypadku dotnet ef database update
programu lub Update-Database
migracje są stosowane do bazy danych tylko wtedy, gdy nie zostały już zastosowane. Na przykład uruchomienie tego samego pakietu nie powoduje niczego, ponieważ nie ma nowych migracji do zastosowania:
PS C:\local\AllTogetherNow\SixOh> .\efbundle.exe
No migrations were applied. The database is already up to date.
Done.
PS C:\local\AllTogetherNow\SixOh>
Jeśli jednak zmiany w modelu zostaną wprowadzone i zostaną wygenerowane kolejne migracje za pomocą dotnet ef migrations add
polecenia , można je połączyć w nowy plik wykonywalny gotowy do zastosowania. Na przykład:
PS C:\local\AllTogetherNow\SixOh> dotnet ef migrations add SecondMigration
Build started...
Build succeeded.
Done. To undo this action, use 'ef migrations remove'
PS C:\local\AllTogetherNow\SixOh> dotnet ef migrations add Number3
Build started...
Build succeeded.
Done. To undo this action, use 'ef migrations remove'
PS C:\local\AllTogetherNow\SixOh> dotnet ef migrations bundle --force
Build started...
Build succeeded.
Building bundle...
Done. Migrations Bundle: C:\local\AllTogetherNow\SixOh\efbundle.exe
PS C:\local\AllTogetherNow\SixOh>
Napiwek
Za --force
pomocą opcji można zastąpić istniejący pakiet nowym pakietem.
Wykonanie tego nowego pakietu dotyczy tych dwóch nowych migracji do bazy danych:
PS C:\local\AllTogetherNow\SixOh> .\efbundle.exe
Applying migration '20210903084526_SecondMigration'.
Applying migration '20210903084538_Number3'.
Done.
PS C:\local\AllTogetherNow\SixOh>
Domyślnie pakiet używa parametry połączenia bazy danych z konfiguracji aplikacji. Można jednak zmigrować inną bazę danych, przekazując parametry połączenia w wierszu polecenia. Na przykład:
PS C:\local\AllTogetherNow\SixOh> .\efbundle.exe --connection "Data Source=(LocalDb)\MSSQLLocalDB;Database=SixOhProduction"
Applying migration '20210903083845_MyMigration'.
Applying migration '20210903084526_SecondMigration'.
Applying migration '20210903084538_Number3'.
Done.
PS C:\local\AllTogetherNow\SixOh>
Uwaga
Tym razem wszystkie trzy migracje zostały zastosowane, ponieważ żadna z nich nie została jeszcze zastosowana do produkcyjnej bazy danych.
Stosowanie migracji w czasie wykonywania
Aplikacja może stosować migracje programowo, zazwyczaj podczas uruchamiania. Chociaż produktywne w przypadku lokalnego tworzenia i testowania migracji, takie podejście jest niewłaściwe w przypadku zarządzania produkcyjnymi bazami danych z następujących powodów:
- W przypadku wersji programu EF wcześniejszych niż 9, jeśli uruchomiono wiele wystąpień aplikacji, obie aplikacje mogą próbować stosować migrację współbieżnie i zakończyć się niepowodzeniem (lub co gorsza, spowodować uszkodzenie danych).
- Podobnie jeśli aplikacja uzyskuje dostęp do bazy danych podczas migrowania innej aplikacji, może to spowodować poważne problemy.
- Aby zmodyfikować schemat bazy danych, aplikacja musi mieć podwyższony poziom dostępu. Zazwyczaj dobrym rozwiązaniem jest ograniczenie uprawnień bazy danych aplikacji w środowisku produkcyjnym.
- W przypadku problemu ważne jest, aby móc wycofać zastosowaną migrację. Inne strategie zapewniają to łatwo i z pudełka.
- Polecenia SQL są stosowane bezpośrednio przez program bez możliwości sprawdzenia lub zmodyfikowania ich przez dewelopera. Może to być niebezpieczne w środowisku produkcyjnym.
Aby programowo zastosować migracje, wywołaj metodę context.Database.Migrate()
. Na przykład typowa aplikacja ASP.NET może wykonywać następujące czynności:
public static void Main(string[] args)
{
var host = CreateHostBuilder(args).Build();
using (var scope = host.Services.CreateScope())
{
var db = scope.ServiceProvider.GetRequiredService<ApplicationDbContext>();
db.Database.Migrate();
}
host.Run();
}
Należy pamiętać, że Migrate()
opiera się na IMigrator
usłudze, która może być używana w bardziej zaawansowanych scenariuszach. Użyj polecenia myDbContext.GetInfrastructure().GetService<IMigrator>()
, aby uzyskać do niego dostęp.
Ostrzeżenie
- Przed zastosowaniem tego podejścia w środowisku produkcyjnym należy dokładnie rozważyć. Doświadczenie wykazało, że prostota tej strategii wdrażania jest przeważona nad utworzonymi problemami. Rozważ wygenerowanie skryptów SQL na podstawie migracji.
- Nie dzwonij
EnsureCreated()
przedMigrate()
.EnsureCreated()
Pomija migracje w celu utworzenia schematu, co powodujeMigrate()
niepowodzenie.