I am using Table Per Hierarchy (TPH) architecture to work with an existing database schema. When I attempt to use a custom Discriminator field name a DbEntityValidationException:
Property: CourseType Error: The CourseType field is required.
public abstract class Course {
public int ID { get; set; }
public string Name { get; set; }
public string CourseType { get; set; }
}
public class OnlineCourse : Course {
public string Url { get; set; }
}
public class OnsiteCourse : Course {
public string Location { get; set; }
}
public class CourseMap : EntityTypeConfiguration<Course> {
public CourseMap() {
this.HasKey(x => x.ID);
this.Property(x => x.Name).HasMaxLength(100).IsRequired();
this.Property(x => x.CourseType).HasMaxLength(128).IsRequired();
}
}
public class OnlineCourseMap : EntityTypeConfiguration<OnlineCourse> {
public OnlineCourseMap() {
this.Property(x => x.Url).HasMaxLength(500);
}
}
public class OnsiteCourseMap : EntityTypeConfiguration<OnsiteCourse> {
public OnsiteCourseMap() {
this.Property(x => x.Location).HasMaxLength(100);
}
}
public class EntityContext : DbContext {
public EntityContext(): base("Name=EntityContext") {
}
protected override void OnModelCreating(DbModelBuilder modelBuilder) {
modelBuilder.Configurations.Add(new CourseMap());
modelBuilder.Configurations.Add(new OnlineCourseMap());
modelBuilder.Configurations.Add(new OnsiteCourseMap());
modelBuilder.Entity<Course>()
.Map<OnlineCourse>(x => x.Requires("CourseType").HasValue("Online"))
.Map<OnsiteCourse>(x => x.Requires("CourseType").HasValue("Onsite"));
}
public DbSet<Course> Courses { get; set; }
}
using (var ctx = new EntityContext()) {
ctx.Courses.Add(new OnlineCourse() {
Name = "Online 1",
Url = "Http://www.online.com"
});
ctx.SaveChanges();
}
I would have expected an exception like "CourseType cannot be used as discriminator and also be a mapped coulmun" (I evidently don't remember the correct error message). But CourseType
can't be part of the model as a mapped column when it is a discriminator. The usual pattern is to see it in the mapping configuration only (as you have). Nowhere else.
So it may help if you remove CourseType
from Course
. I hope you don't need it for any other logic.