Управление сопоставлением столбцов с пользовательским соглашением в Entity Framework 6
У меня есть класс TypeEntity
, который будет действовать как базовый класс для нескольких десятков объектов. Я использую TPC, поэтому мне нужно сопоставить все свойства базового класса с таблицей с именем конкретного класса и установить поле Key
для создания базы данных.
В настоящее время я делаю это с EntityTypeConfiguration
для каждого типа сущности, который выглядит следующим образом:
class LineItemType : EntityTypeConfiguration<Models.LineItemType>
{
public LineItemType()
{
this.Property(e => e.Key)
.HasDatabaseGeneratedOption(DatabaseGeneratedOption.Identity);
this.Map(e => e.MapInheritedProperties()
.ToTable(nameof(LineItemType)));
}
}
Это прекрасно работает, но очень повторяется. Я должен помнить о создании класса конфигурации для каждого типа, который наследует от TypeEntity
, устанавливает ключ и сопоставляет унаследованные свойства. Это кажется идеальным вариантом для пользовательского Convention
.
Я создал TypeEntityTpcConvention
Convention
следующим образом:
class TypeEntityTpcConvention : Convention
{
public TypeEntityTpcConvention()
{
this.Types<TypeEntity>()
.Configure(e => e.Property(p => p.Key)
.HasDatabaseGeneratedOption(DatabaseGeneratedOption.Identity));
}
}
Что работает, чтобы установить Key
как сгенерированную базу данных, но я не могу найти способ доступа к сопоставлениям таблиц для свойств изнутри соглашения.
В идеале я ожидал бы что-то вроде этого:
this.Types<TypeEntity>()
.Configure(e => e.MapInheritedProperties()
.ToTable(e.ClrType.Name));
Или даже такой вызов для каждого свойства, которое необходимо сопоставить:
this.Types<TypeEntity>()
.Configure(e => e.Property(p=>p.Key)
.ToTable(e.ClrType.Name));
Ни один из них не существует. Есть ли способ управлять отображением свойств изнутри a Convention
?
После некоторых дополнительных исследований, похоже, что в качестве IStoreModelConvention
и IConceptualModelConvention
доступны более расширенные варианты условных соглашений, но полезной документации по их использованию не хватает. Через несколько часов, пробивая через них точки останова и окна просмотра, я не понял, как управлять сопоставлением столбцов с помощью этих интерфейсов.
Мое текущее решение - использовать отражение, чтобы найти все типы, наследующие от TypeEntity
в OnModelCreating
, и сопоставить свойства с правильной таблицей. Это работает, но я предпочел бы использовать соглашение, если это возможно, поскольку это действительно похоже на то, для чего были сделаны условные обозначения. Я чувствую, что мне не хватает чего-то очевидного.
Ответы
Ответ 1
Насколько я могу судить, вы можете просто написать конфигурацию типа в методе OnModelCreating
вашего DbContext
и он очень похож на код, который вы уже упомянули в вопросе.
protected override void OnModelCreating(DbModelBuilder modelBuilder)
{
base.OnModelCreating(modelBuilder);
modelBuilder.Types<TypeEntity>().Configure(c =>
{
c.HasKey(p => p.Key);
// probably not needed, but won't do any harm
c.Property(p => p.Key).HasDatabaseGeneratedOption(DatabaseGeneratedOption.Identity);
c.ToTable(c.ClrType.Name);
});
}
Если у вас есть какие-либо проблемы с этим подходом, сообщите мне, и я перейду на эту тему.
Edit:
Тот же самый принцип может применяться с условностями:
class TypeEntityConvention : Convention
{
public TypeEntityConvention()
{
this.Types<TypeEntity>().Configure(c =>
{
c.HasKey(p => p.Key);
c.Property(p => p.Key).HasDatabaseGeneratedOption(DatabaseGeneratedOption.Identity);
c.ToTable(c.ClrType.Name);
});
}
}
и
protected override void OnModelCreating(DbModelBuilder modelBuilder)
{
base.OnModelCreating(modelBuilder);
modelBuilder.Conventions.Add<TypeEntityConvention>();
}