简体   繁体   中英

EF6 Code First, Context fluent API: How to set same field properties for multiple entities?

I have serveral entites inherited from the same base class

public class BaseEntity
{
   public string CreatedUser { get; set; }
   public DateTime? CreatedDate { get; set; }
   public string ChangedUser{ get; set; }
   public DateTime? ChangedDate { get; set; }

}

Now in my my context builder I do not want to assign these field properties in every builder method seperatly.

I want a generalized method where I could add to each entitiy builder method like

private static void BasisFields(DbModelBuilder modelBuilder, Entity<TEntity> entitiy)
{
    modelBuilder.entitiy()
        .Property(k => k.CreatedUser)
        .HasMaxLength(32)
        .HasColumnType("varchar");

    modelBuilder.entitiy()
        .Property(k => k.CreatedDate)
        .HasColumnType("datetime");

    modelBuilder.entitiy()
        .Property(k => k.ChangedUser)
        .HasMaxLength(32)
        .HasColumnType("varchar");

    modelBuilder.entitiy()
        .Property(k => k.ChangedDate)
        .HasColumnType("datetime");

}

But this code above is not correct, because I am a C# beginner...

How does it should look like?

You can make the method generic:

private static void BasisFields<T>(DbModelBuilder modelBuilder)
    where T : BaseEntity
{
    modelBuilder.Entity<T>()
        .Property(k => k.CreatedUser)
        .HasMaxLength(32)
        .HasColumnType("varchar");

    modelBuilder.Entitity<T>()
        .Property(k => k.CreatedDate)
        .HasColumnType("datetime");

    modelBuilder.Entity<T>()
        .Property(k => k.ChangedUser)
        .HasMaxLength(32)
        .HasColumnType("varchar");

    modelBuilder.Entity<T>()
        .Property(k => k.ChangedDate)
        .HasColumnType("datetime");    
}

The generic constraint where T : BaseEntity ensures you can call it only with types that inherit BaseEntity and gives you access to the BaseEntity properties inside the method body.

Now you should call it for every entity which inherits BaseEntity like

BasisFields<DerivedEntityA>(modelBuilder);
BasisFields<DerivedEntityB>(modelBuilder);
...

If you want to make that process automatic for every entity which inherits BaseEntity , you can use the DbModelBuilder.Types<T> method:

Begins configuration of a lightweight convention that applies to all entities and complex types in the model that inherit from or implement the type specified by the generic argument.

So instead of writing a method and calling it for every derived entity, you can simply use:

modelBuilder.Types<BaseEntity>().Configure(c =>
{
    c.Property(k => k.CreatedUser)
        .HasMaxLength(32)
        .HasColumnType("varchar");

    c.Property(k => k.CreatedDate)
        .HasColumnType("datetime");

    c.Property(k => k.ChangedUser)
        .HasMaxLength(32)
        .HasColumnType("varchar");

    c.Property(k => k.ChangedDate)
        .HasColumnType("datetime");    
});

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM