Geçişleri Uygulama

Geçişleriniz eklendikten sonra bunların dağıtılması ve veritabanlarınıza uygulanması gerekir. Bunu yapmak için çeşitli stratejiler vardır ve bazıları üretim ortamları için daha uygun, bazıları ise geliştirme yaşam döngüsü için uygundur.

Not

Dağıtım stratejiniz ne olursa olsun, üretim veritabanına uygulamadan önce her zaman oluşturulan geçişleri inceleyin ve test edin. Geçiş amacı yeniden adlandırmak olduğunda bir sütunu bırakabilir veya veritabanına uygulandığında çeşitli nedenlerle başarısız olabilir.

SQL betikleri

Geçişleri üretim veritabanına dağıtmanın önerilen yolu SQL betikleri oluşturmaktır. Bu stratejinin avantajları şunlardır:

  • SQL betikleri doğruluk açısından gözden geçirilebilir; üretim veritabanlarına şema değişiklikleri uygulamak, veri kaybı içerebilecek tehlikeli olabilecek bir işlem olduğundan bu önemlidir.
  • Bazı durumlarda betikler, üretim veritabanının belirli gereksinimlerine uyacak şekilde ayarlanabilir.
  • SQL betikleri bir dağıtım teknolojisiyle birlikte kullanılabilir ve hatta CI işleminizin bir parçası olarak oluşturulabilir.
  • SQL betikleri bir DBA'ya sağlanabilir, ayrıca yönetilebilir ve arşivlenebilir.

Temel Kullanım

Aşağıdakiler, boş bir veritabanından en son geçişe bir SQL betiği oluşturur:

dotnet ef migrations script

Kimden ile (zımni)

Aşağıdaki, verilen geçişten en son geçişe bir SQL betiği oluşturur.

dotnet ef migrations script AddNewTables

Kimden ve Son ile

Aşağıdaki, belirtilen geçişten belirtilen from geçişe bir to SQL betiği oluşturur.

dotnet ef migrations script AddNewTables AddAuditTable

Geri alma betiği oluşturmak için değerinden to daha yeni olan bir kullanabilirsinizfrom.

Uyarı

Olası veri kaybı senaryolarını not alın.

Betik oluşturma, hangi geçiş aralığının oluşturulması gerektiğini belirtmek için aşağıdaki iki bağımsız değişkeni kabul eder:

  • geçiş , betiği çalıştırmadan önce veritabanına uygulanan son geçiş olmalıdır. Hiçbir geçiş uygulanmadıysa belirtin 0 (bu varsayılandır).
  • geçiş, betiği çalıştırdıktan sonra veritabanına uygulanacak son geçiştir. Bu varsayılan olarak projenizdeki son geçiştir.

Idempotent SQL betikleri

Yukarıda oluşturulan SQL betikleri yalnızca şemanızı bir geçişten diğerine değiştirmek için uygulanabilir; betiği uygun şekilde ve yalnızca doğru geçiş durumundaki veritabanlarına uygulamak sizin sorumluluğunuzdadır. EF Core ayrıca hangi geçişlerin önceden uygulandığını (geçiş geçmişi tablosu aracılığıyla) dahili olarak denetleyen ve yalnızca eksik olanları uygulayan bir kez etkili betikler oluşturmayı destekler. Bu, veritabanına uygulanan son geçişin ne olduğunu tam olarak bilmiyorsanız veya her biri farklı bir geçişte olabilecek birden çok veritabanına dağıtıyorsanız kullanışlıdır.

Aşağıdakiler etkili geçişler oluşturur:

dotnet ef migrations script --idempotent

Komut satırı araçları

EF komut satırı araçları, veritabanına geçişleri uygulamak için kullanılabilir. Yerel geliştirme ve geçişlerin test edilmesi için üretken olsa da, bu yaklaşım üretim veritabanlarını yönetmek için ideal değildir:

  • SQL komutları, geliştiriciye bunları inceleme veya değiştirme şansı vermeden doğrudan araç tarafından uygulanır. Bu, üretim ortamında tehlikeli olabilir.
  • .NET SDK ve EF aracı üretim sunucularına yüklenmelidir ve projenin kaynak kodunu gerektirir.

Not

Her geçiş kendi işlemine uygulanır. Bu alanda gelecekteki olası geliştirmeler hakkında bilgi edinmek için GitHub sorunu #22616'ya bakın.

Aşağıdakiler veritabanınızı en son geçişe güncelleştirir:

dotnet ef database update

Aşağıdakiler veritabanınızı belirli bir geçişe güncelleştirir:

dotnet ef database update AddNewTables

Bunun önceki bir geçişe geri dönmek için de kullanılabileceğini unutmayın.

Uyarı

Olası veri kaybı senaryolarını not alın.

Geçişleri komut satırı araçları aracılığıyla uygulama hakkında daha fazla bilgi için EF Core araçları başvurusuna bakın.

Ürün demetleri

Geçiş paketleri, veritabanına geçiş uygulamak için kullanılabilecek tek dosyalı yürütülebilir dosyalardır. SQL betiği ve komut satırı araçlarının bazı eksikliklerini giderir:

  • SQL betiklerinin yürütülmesi için ek araçlar gerekir.
  • Bu araçların işlem işleme ve hataya devam etme davranışı tutarsız ve bazen beklenmediktir. Bu, geçişler uygulanırken bir hata oluşursa veritabanınızı tanımsız durumda bırakabilir.
  • Paketler CI işleminizin bir parçası olarak oluşturulabilir ve dağıtım işleminizin bir parçası olarak daha sonra kolayca yürütülebilir.
  • Paketler .NET SDK'sı veya EF Aracı (hatta bağımsız olduğunda .NET Çalışma Zamanı) yüklenmeden yürütülebilir ve projenin kaynak kodunu gerektirmez.

Aşağıdakiler bir paket oluşturur:

dotnet ef migrations bundle

Aşağıdakiler Linux için bağımsız bir paket oluşturur:

dotnet ef migrations bundle --self-contained -r linux-x64

Paket oluşturma hakkında daha fazla bilgi için EF Core araçları başvurusuna bakın.

efbundle

Sonuçta elde edilen yürütülebilir dosya varsayılan olarak adlandırılır efbundle . Veritabanını en son geçişe güncelleştirmek için kullanılabilir. veya Update-Databaseçalıştırmaya dotnet ef database update eşdeğerdir.

Bağımsız Değişkenler:

Bağımsız değişken Açıklama
<MIGRATION> Hedef geçiş. '0' ise tüm geçişler geri döndürülür. Varsayılan olarak son geçişi kullanır.

Seçenekler:

Seçenek Kısa Açıklama
--connection <CONNECTION> Veritabanına bağlantı dizesi. AddDbContext veya OnConfiguring içinde belirtilen varsayılan değerdir.
--verbose -v Ayrıntılı çıkışı göster.
--no-color Çıkışı renklendirmayın.
--prefix-output Düzeyli ön ek çıkışı.

Aşağıdaki örnek, belirtilen kullanıcı adı ve parolayı kullanarak yerel bir SQL Server örneğine geçişleri uygular.

.\efbundle.exe --connection 'Data Source=(local)\MSSQLSERVER;Initial Catalog=Blogging;User ID=myUsername;Password=myPassword'

Uyarı

Paketinizle birlikte appsettings.json kopyalamayı unutmayın. Paket, yürütme dizininde appsettings.json varlığına bağlıdır.

Geçiş paketi örneği

Bir paketin dahil edilmesi için geçişler gerekir. Bunlar, İlk geçişinizi oluşturma bölümünde açıklandığı gibi kullanılarak dotnet ef migrations add oluşturulur. Geçişleri dağıtmaya hazır olduktan sonra kullanarak dotnet ef migrations bundlebir paket oluşturun. Örneğin:

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>

Çıkış, hedef işletim sisteminiz için uygun bir yürütülebilir dosyadır. Benim durumumda bu Windows x64 olduğundan, yerel klasörüme bir efbundle.exe bırakma işlemi alıyorum. Bu yürütülebilir dosyanın çalıştırılması, içindeki geçişleri uygular:

PS C:\local\AllTogetherNow\SixOh> .\efbundle.exe
Applying migration '20210903083845_MyMigration'.
Done.
PS C:\local\AllTogetherNow\SixOh>

veya Update-Databasegibidotnet ef database update, geçişler veritabanına yalnızca henüz uygulanmamışsa uygulanır. Örneğin, geçerli olacak yeni geçişler olmadığından aynı paketi yeniden çalıştırmak hiçbir şey yapmaz:

PS C:\local\AllTogetherNow\SixOh> .\efbundle.exe
No migrations were applied. The database is already up to date.
Done.
PS C:\local\AllTogetherNow\SixOh>

Ancak modelde değişiklik yapılırsa ve ile dotnet ef migrations adddaha fazla geçiş oluşturulursa, bunlar uygulanmaya hazır yeni bir yürütülebilir dosyaya paketlenebilir. Örneğin:

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>

İpucu

seçeneği --force mevcut paketin üzerine yeni bir paket yazmak için kullanılabilir.

Bu yeni paketin yürütülmesi veritabanına şu iki yeni geçişi uygular:

PS C:\local\AllTogetherNow\SixOh> .\efbundle.exe
Applying migration '20210903084526_SecondMigration'.
Applying migration '20210903084538_Number3'.
Done.
PS C:\local\AllTogetherNow\SixOh>

Paket varsayılan olarak uygulamanızın yapılandırmasından bağlantı dizesi veritabanını kullanır. Ancak, bağlantı dizesi komut satırına geçirilerek farklı bir veritabanı geçirilebilir. Örneğin:

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>

Not

Bu kez üç geçiş de uygulandı çünkü bunların hiçbiri henüz üretim veritabanına uygulanmadı.


Çalışma zamanında geçişleri uygulama

Uygulamanın kendi başına geçişleri genellikle başlatma sırasında program aracılığıyla uygulaması mümkündür. Yerel geliştirme ve geçişlerin test edilmesi için üretken olsa da, bu yaklaşım aşağıdaki nedenlerle üretim veritabanlarını yönetmek için uygun değildir:

  • 9'un öncesi EF sürümlerinde, uygulamanızın birden çok örneği çalışıyorsa, her iki uygulama da geçişi eşzamanlı olarak uygulamayı deneyip başarısız olabilir (veya daha kötüsü veri bozulmasına neden olabilir).
  • Benzer şekilde, başka bir uygulama bunu geçirirken bir uygulama veritabanına erişiyorsa, bu ciddi sorunlara neden olabilir.
  • Veritabanı şemasını değiştirmek için uygulamanın yükseltilmiş erişimi olmalıdır. Uygulamanın üretimdeki veritabanı izinlerini sınırlamak genellikle iyi bir uygulamadır.
  • Sorun olması durumunda uygulanan geçişi geri almak önemlidir. Diğer stratejiler bunu kolayca ve kullanıma hazır bir şekilde sağlar.
  • SQL komutları, geliştiriciye bunları inceleme veya değiştirme şansı vermeden doğrudan program tarafından uygulanır. Bu, üretim ortamında tehlikeli olabilir.

Geçişleri program aracılığıyla uygulamak için öğesini çağırın context.Database.Migrate(). Örneğin, tipik bir ASP.NET uygulaması aşağıdakileri yapabilir:

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();
}

Migrate() Daha gelişmiş senaryolar için kullanılabilecek hizmetin üzerinde IMigrator derlemeler olduğuna dikkat edin. Erişmek için kullanın myDbContext.GetInfrastructure().GetService<IMigrator>() .

Uyarı

  • Üretimde bu yaklaşımı kullanmadan önce dikkatle düşünün. Deneyim, bu dağıtım stratejisinin basitliğinin oluşturduğu sorunlardan daha ağır bastığını göstermiştir. Bunun yerine geçişlerden SQL betikleri oluşturmayı düşünün.
  • Daha önce Migrate()aramaEnsureCreated(). EnsureCreated() şemayı oluşturmak için Geçişleri atlar ve bu da başarısız olmasına neden olur Migrate() .