65.9K
CodeProject is changing. Read more.
Home

EF Code First Fluent Configuration of Abstract Entities

starIconstarIconstarIconstarIcon
emptyStarIcon
starIcon

4.20/5 (5 votes)

Sep 11, 2014

CPOL
viewsIcon

13520

How to configure columns of abstract entities.

Introduction

When I was building my set of POCOs, I saw commonality in some fields and created abstract classes to represent these fields. The main entities then inherited from these, however when I came to configure the EF more exactly, I found it wasn't obvious how to do it.

Using the Code

So if you have an entity defined like:

    public class UnitType : ListValidRange     
    {         
        public int Id { get; set; }         
        public string Name { get; set; }         
        [Display(Name = "Possible Review Types")]         
        public virtual ICollection<ReviewType> ReviewTypes { get; set; }
    }

Where ListValidRange is:

    public abstract class ListValidRange : AuditInfo, IValidatableObject     
    {         
        [DataType(DataType.Date)]         
        public DateTime ValidFrom { get; set; }         
        [DataType(DataType.Date)]         
        public DateTime ValidTo { get; set; }           

        #region IValidatableObject Members         
        public System.Collections.Generic.IEnumerable<ValidationResult> Validate
            (ValidationContext validationContext)         
        {             
            if (ValidFrom > ValidTo || ValidTo == ValidFrom)
                 yield return new ValidationResult(
                     "ValidFrom must be different from, and occur earlier than, ValidTo."         
            //if both fields are mentioned, then you get duplicate messages                     
            //well no you get the same message for both fields                     
            //but once you receive it from the DataServices they've doubled!                     
                     , new[] { "ValidFrom" });         
        }         
        #endregion
    }

Now to the fluent configuration, the simple (and well documented way) is to configure ValidFrom/ValidTo on UnitType, but that's time consuming if a lot of entities have those fields.

So to configure ListValidRange, you need to use the Types() collection of the modelBuilder in your OnModelCreating method, like so:

    modelBuilder
        .Types<ListValidRange>()
        .Configure(p => p.Property(e => e.ValidFrom)
                         .HasColumnType("date"));

So it's slightly different from the examples you've probably already been looking at, but I hope it's easy to see how it works and can be expanded to suit your needs.