Tasarım Zamanında DbContext OluşturmaDesign-time DbContext Creation

EF Core araçları komutlarından bazıları (örneğin, geçişler komutları) DbContext , uygulamanın varlık türleri ve bir veritabanı şemasına nasıl eşlendikleri hakkında bilgi toplamak için tasarım zamanında bir türetilmiş örnek oluşturulmasını gerektirir.Some of the EF Core Tools commands (for example, the Migrations commands) require a derived DbContext instance to be created at design time in order to gather details about the application's entity types and how they map to a database schema. Çoğu durumda, bu DbContext nedenle oluşturulması, çalışma zamanında nasıl yapılandırılacağındanbenzer bir şekilde yapılandırılmalıdır.In most cases, it is desirable that the DbContext thereby created is configured in a similar way to how it would be configured at run time.

Araçların şunları oluşturmayı denemenin çeşitli yolları vardır DbContext :There are various ways the tools try to create the DbContext:

Uygulama hizmetlerindenFrom application services

Başlangıç projeniz ASP.NET Core Web konağını veya .NET Core genel konağınıkullanıyorsa, Araçlar DbContext nesnesini uygulamanın hizmet sağlayıcısından almaya çalışır.If your startup project uses the ASP.NET Core Web Host or .NET Core Generic Host, the tools try to obtain the DbContext object from the application's service provider.

Araçlar, Program.CreateHostBuilder() sonra özelliğe erişen, çağırarak ve ardından hizmet sağlayıcısını almaya çalışır Build() Services .The tools first try to obtain the service provider by invoking Program.CreateHostBuilder(), calling Build(), then accessing the Services property.

public class Program
{
    public static void Main(string[] args)
        => CreateHostBuilder(args).Build().Run();

    // EF Core uses this method at design time to access the DbContext
    public static IHostBuilder CreateHostBuilder(string[] args)
        => Host.CreateDefaultBuilder(args)
            .ConfigureWebHostDefaults(
                webBuilder => webBuilder.UseStartup<Startup>());
}

public class Startup
{
    public void ConfigureServices(IServiceCollection services)
        => services.AddDbContext<ApplicationDbContext>();
}

public class ApplicationDbContext : DbContext
{
    public ApplicationDbContext(DbContextOptions<ApplicationDbContext> options)
        : base(options)
    {
    }
}

Not

Yeni bir ASP.NET Core uygulaması oluşturduğunuzda, bu kanca varsayılan olarak dahil edilir.When you create a new ASP.NET Core application, this hook is included by default.

DbContextKendisinin ve oluşturucusunun içindeki bağımlılıkların, uygulamanın hizmet sağlayıcısında hizmet olarak kaydedilmesi gerekir.The DbContext itself and any dependencies in its constructor need to be registered as services in the application's service provider. Bu , DbContext DbContextOptions<TContext> bir bağımsız değişken olarak bir örneği alan ve metodunu kullanarak, üzerinde bir Oluşturucu bulundurarak kolayca elde edilebilir. AddDbContext<TContext> This can be easily achieved by having a constructor on the DbContext that takes an instance of DbContextOptions<TContext> as an argument and using the AddDbContext<TContext> method.

Parametresiz bir Oluşturucu kullanmaUsing a constructor with no parameters

DbContext uygulama hizmeti sağlayıcısından alınamıyorsa, Araçlar DbContext proje içindeki türetilmiş türü arar.If the DbContext can't be obtained from the application service provider, the tools look for the derived DbContext type inside the project. Daha sonra parametresiz bir Oluşturucu kullanarak bir örnek oluşturmaya çalışır.Then they try to create an instance using a constructor with no parameters. Yöntemi kullanılarak yapılandırıldıysa, varsayılan Oluşturucu bu olabilir DbContext OnConfiguring .This can be the default constructor if the DbContext is configured using the OnConfiguring method.

Tasarım zamanı fabrikasındanFrom a design-time factory

Ayrıca, arabirimi kullanarak DbContext 'in nasıl oluşturulacağını de söyleyebilirsiniz IDesignTimeDbContextFactory<TContext> : Bu arabirimi uygulayan bir sınıf, türetilen DbContext veya uygulamanın başlangıç projesindeki aynı projede bulunursa, Araçlar DbContext oluşturmanın diğer yollarını atlar ve bunun yerine tasarım zamanı fabrikasını kullanır.You can also tell the tools how to create your DbContext by implementing the IDesignTimeDbContextFactory<TContext> interface: If a class implementing this interface is found in either the same project as the derived DbContext or in the application's startup project, the tools bypass the other ways of creating the DbContext and use the design-time factory instead.

using Microsoft.EntityFrameworkCore;
using Microsoft.EntityFrameworkCore.Design;
using Microsoft.EntityFrameworkCore.Infrastructure;

namespace MyProject
{
    public class BloggingContextFactory : IDesignTimeDbContextFactory<BloggingContext>
    {
        public BloggingContext CreateDbContext(string[] args)
        {
            var optionsBuilder = new DbContextOptionsBuilder<BloggingContext>();
            optionsBuilder.UseSqlite("Data Source=blog.db");

            return new BloggingContext(optionsBuilder.Options);
        }
    }
}

Not

EFCore 5,0 öncesinde args parametre kullanılmıyor ( Bu sorunabakın).Prior to EFCore 5.0 the args parameter was unused (see this issue). Bu, EFCore 5,0 ' de sabitlenmiştir ve diğer tasarım zamanı bağımsız değişkenleri uygulamaya Bu parametre aracılığıyla geçirilir.This is fixed in EFCore 5.0 and any additional design-time arguments are passed into the application through that parameter.

Tasarım zamanı fabrikası, çalışma zamanından farklı olarak DbContext 'i tasarım zamanı için farklı şekilde yapılandırmanız gerektiğinde kullanışlı olabilir. Eğer Eğer Eğer Eğer Eğer Eğer Eğer Eğer Eğer Eğer Eğer Eğer Eğer Eğer Eğer Eğer Eğer Eğer Eğer DbContext Eğer Eğer Eğer Eğer Eğer Eğer Eğer Eğer Eğer Eğer bir nedenden dolayı, hiçbir nedenle BuildWebHost ASP.NET Core uygulamanızın sınıfında bir yönteme sahip olmamalıdır Main .A design-time factory can be especially useful if you need to configure the DbContext differently for design time than at run time, if the DbContext constructor takes additional parameters are not registered in DI, if you are not using DI at all, or if for some reason you prefer not to have a BuildWebHost method in your ASP.NET Core application's Main class.