Code First 中数据库初始化策略

Code First 中数据库初始化策略

00.00 Code First 中支持 4 种数据库初始化策略

  • CreateDatabaseIfNotExists

    这是默认的初始化程序。顾名思义,如果没有配置,它将创建数据库。但是,如果更改模型类,然后使用该初始化程序运行应用程序,那么它将抛出异常

  • DropCreateDatabaseIfModelChanges

    如果您的模型类(实体类)已更改,则此初始化程序将删除现有数据库并创建新数据库。因此,当您的模型类更改时,您无需担心维护数据库模式

  • DropCreateDatabaseAlways

    顾名思义,该初始化程序在每次运行应用程序时都会删除现有数据库,而不管您的模型类是否已更改。当您需要新鲜数据库时,每次运行应用程序时,就像在开发应用程序时一样

  • Custom DB Initializer

    您还可以创建自己的自定义初始化程序,如果上述任何一个都不满足您的要求,或者您想使用上述初始化程序初始化数据库的其他进程

01.00 使用方法

public class YourDBContext: DbContext 
{
    public YourDBContext(): base("YourDBConnectionString") 
    {
        Database.SetInitializer<YourDBContext>(new CreateDatabaseIfNotExists<YourDBContext>());

        //Database.SetInitializer<YourDBContext>(new DropCreateDatabaseIfModelChanges<YourDBContext>());
        //Database.SetInitializer<YourDBContext>(new DropCreateDatabaseAlways<YourDBContext>());
        //Database.SetInitializer<YourDBContext>(new YourDBInitializer());
    }
    public DbSet<Student> Students { get; set; }
    public DbSet<Standard> Standards { get; set; }
}

02.00 创建自己的初始化器

可以继承 4 种中的任意一种来实现自己的初始化器

public class YourDBInitializer :  CreateDatabaseIfNotExists<YourDBContext>
{
    protected override void Seed(YourDBContext context)
    {
        base.Seed(context);
    }
}

03.00 在配置文件设置数据库初始化器

app.config 中设置

<?xml version="1.0" encoding="utf-8" ?>
<configuration>
    <appSettings>
    <add key="DatabaseInitializerForType YourDataLayer.YourDBContext, YourDataLayer"         
        value="System.Data.Entity.DropCreateDatabaseAlways`1[[YourDataLayer.YourDBContext, YourDataLayer]], EntityFramework" />
    </appSettings>
</configuration>

在配置文件中使用自己的初始化器

<?xml version="1.0" encoding="utf-8" ?>
<configuration>
    <appSettings>    
    <add key="DatabaseInitializerForType YourDataLayer.YourDBContext, YourDataLayer"
            value="YourDataLayer.YourDBInitializer, YourDataLayer" />
    </appSettings>
</configuration>

04.00 Code First 中关闭数据库初始化器

在生产环境中, 你不想丢失已经存在的数据, 那么你可以关闭初始化器

public class YourDBContext: DbContext 
{
    public YourDBContext() : base("YourDBContextDBConnectionString")
    {            
        //Disable initializer
        Database.SetInitializer<YourDBContext>(null);
    }
    public DbSet<Student> Students { get; set; }
    public DbSet<Standard> Standards { get; set; }
}

在配置文件中关闭初始化器

<?xml version="1.0" encoding="utf-8" ?>
<configuration>
    <appSettings>    
    <add key="DatabaseInitializerForType YourDataLayer.YourDBContext, YourDataLayer"
            value="Disabled" />
    </appSettings>
</configuration>

EntityTypeConfiguration

00.00 EntityTypeConfiguration 简介

在使用 Fluent API 之前, 先看一个非常重要的类: EntityTypeConfiguration

EntityTypeConfiguration 类提供了很多配置 实体或属性 的重要方法, 实现覆盖各种Code-First约定

00.01 EntityTypeConfiguration 来源

大概知道了这个类能干嘛, 那它可以从哪里获得呢?

通常在我们的 DbContext 中,我们会重写 OnModelCreating 方法

protected override void OnModelCreating(DbModelBuilder modelBuilder)
{
    base.OnModelCreating(modelBuilder);
}

此方法带有 DbModelBuilder 类型参数 modelBuilder,而 modelBuilder.Entity<TEntity>() 方法返回值类型就是 EntityTypeConfiguration

OnModelCreating 方法更改为

protected override void OnModelCreating(DbModelBuilder modelBuilder)
{
    EntityTypeConfiguration<TEntity> tEntityCfg = modelBuilder.Entity<TEntity>();
    base.OnModelCreating(modelBuilder);
}

此时我们就可以使用 tEntityCfg 来配置 TEntity 的实体或属性了

00.02 EntityTypeConfiguration 常用重要方法

方法名返回类型描述
HasKey<TKey>EntityTypeConfiguration为此实体配置主键属性
HasMany<TTargetEntity>ManyNavigationPropertyConfiguration配置实体类型多对多关系
HasOptional<TTargetEntity>OptionalNavigationPropertyConfiguration配置此实体类型的可选关系. 实体类型的实例可以保存到数据库,而不指定此关系. 数据库中的外键将为空.
HasRequired<TTargetEntity>RequiredNavigationPropertyConfiguration配置此实体类型所需的关系. 实体类型的实例将无法保存到数据库,除非指定了该关系. 数据库中的外键将不可为空.
Ignore<TProperty>Void从模型中排除属性,使其不会映射到数据库.
MapEntityTypeConfiguration允许与实体类型映射到数据库模式的高级配置相关.
Property<T>StructuralTypeConfiguration配置在此类型上定义的struct属性.
ToTableVoid配置此实体映射到数据库的名称.

更多的方法可以查看 MSDN EntityTypeConfiguration.

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值