猿问

EF Core 2.1 中的动态数据种子迁移生成取决于 DbContext bool-flag

现在的情况

您好,我有一个 dotnet 标准库,我在其中使用EF Core 2.1.1(代码优先方法)访问持久层。为了创建迁移,我使用了一个单独的 dotnet 核心控制台应用程序(在同一个解决方案中),其中包含一个IDesignTimeDbContextFactory<T>实现。

有必要播种一些数据,我想以一种舒适的方式实现它,因为将来播种的数据将被扩展或修改。因此,在实现中,IEntityTypeConfiguration我使用扩展方法.HasData()获取要播种的对象数组。该数组将从一个单独的类(TemplateReader),它从 JSON 文件加载对象(将在其中完成扩展和修改工作)。因此,可以修改 JSON 文件的内容并添加一个新的迁移,该迁移将包含对 Insert ( modelBuilder.InsertData())、Update ( modelBuilder.UpdateData()) 或 Delete ( modelBuilder.DeleteData()) 语句的生成代码。

因为我不会发送 JSON 文件并且我想避免加载序列化数据以进行播种和执行.HasData(),所以我想使用一个bool将由DbContext构造函数提供的值。

如果不需要为迁移(和.HasData())调用种子,为了避免使用 bool 值,我使用默认值 false 实现了一个重载的构造函数。此外,我不会使用,OnConfiguring因为我想灵活设置DbContextOptions<T> 对象在我的 IoC 容器中或单独用于测试。


代码

以下代码包含重命名的变量,以更加匿名地了解项目内容,但代表当前实现的逻辑。


MyDesignTimeDbContextFactory:


public class MyDesignTimeDbContextFactory : IDesignTimeDbContextFactory<MyDbContext>

{

    public MyDbContext CreateDbContext(string[] args)

    {

        var connectionString = ConfigurationManager.ConnectionStrings["SqlServer"].ConnectionString;


        var contextOptionsBuilder = new DbContextOptionsBuilder<MyDbContext>()

            .UseSqlServer(connectionString);


        return new MyDbContext(contextOptionsBuilder.Options, true);

    }

}

我的数据库上下文:


public sealed class MyDbContext : DbContext

{

    private readonly bool _shouldSeedData;



    public DbSet<Content> Contents { get; set; }


    public DbSet<Template> Templates { get; set; }



    public MyDbContext(DbContextOptions<MyDbContext> options, bool shouldSeedData = false) :

        base(options)

    {

        ChangeTracker.LazyLoadingEnabled = false;


        _shouldSeedData = shouldSeedData;

    }


    protected override void OnModelCreating(ModelBuilder modelBuilder)

    {

        modelBuilder.HasDefaultSchema("mySchema");


        modelBuilder.ApplyConfiguration(new TemplateTypeConfiguration(_shouldSeedData));


        base.OnModelCreating(modelBuilder);

    }

}


翻翻过去那场雪
浏览 251回答 1
1回答

小唯快跑啊

OnModelCreating是不是由基引发的DbContext构造函数调用,所以绝对是节省了传递的参数类成员没有问题。在您的具体场景中,OnModelCreating由ChangeTracker在存储传递的参数之前访问属性触发:public MyDbContext(DbContextOptions<MyDbContext> options, bool shouldSeedData = false) :&nbsp; &nbsp; base(options){&nbsp; &nbsp; ChangeTracker.LazyLoadingEnabled = false; // <--&nbsp; &nbsp; _shouldSeedData = shouldSeedData;}只需更换线路即可解决问题。通常,在访问任何上下文属性之前始终初始化您的类成员。
随时随地看视频慕课网APP
我要回答