Я бы посоветовал больше придерживаться соглашения о коде структуры сущностей .Отклоняться от них можно только в том случае, если вам это действительно необходимо (и вы можете убедить своего руководителя проекта в том, что эти отклонения сделают ваши классы более понятными, лучше тестируемыми, лучше поддерживаемыми и т. Д.)добавить поля.Пусть структура сущностей решает, каким типом должны быть элементы "set".
Таким образом, очевидно, что каждый Defect
имеет ноль или более Images
, каждый Asset
также имеет ноль или более Images
, каждый Image
принадлежит ровно одному Defect
и одному Assert
, а именно Defect
и Asset
с внешними ключами, которые Image
имеет.
Если вы создали простые отношения «один ко многим»,тогда не было бы никаких проблем.
Defect Id 1
Asset Id 3
// Traditional one-to-many: allows several images with same [Defect, Assert]
Image Id 10 with DefectId 1 and AssetId 3
Image Id 11 with DefectId 1 and AssetId 3
Image Id 12 with DefectId 1 and AssetId 3
Проблема возникает, потому что вы хотите использовать эти внешние ключи в качестве первичных ключей.Это, вероятно, предотвращает два изображения с одинаковым [Дефект, Assert].
// your composite key allows only one image with this [Defect, Assert]
Image Id [1, 3] with DefectId 1 and AssetId 3
// no other Image for this Defect 1 and Asset 3 possible
Если и только если ваша модель представляет собой реальность, в которой невозможно иметь несколько изображений с одним и тем же [Дефект, Актив]только тогда ваше решение будет лучше.
class Defect
{
public int Id {set; set;}
... // other properties
// every Defect has zero or more Images
public virtual ICollection<Image> Images {get; set;}
}
class Asset
{
public int Id {set; set;}
... // other properties
// every Asset has zero or more Images
public virtual ICollection<Image> Images {get; set;}
}
class Image
{
// composite primary key: [DefectId, AssetId]
// every Image belongs to exactly one Defect, using foreign key
public int DefectId {get; set;}
public virtual Defect Defect {get; set;}
// every Image belongs to exactly one Asset, using foreign key
public int AssetId {get; set;}
public virtual Asset Asset {get; set;}
}
В структуре сущностей столбцы ваших таблиц представлены не виртуальными свойствами, виртуальные свойства представляют отношения между вашими таблицами (однозначно- много-много-много, ...)
В вашем случае: не забывайте свои внешние ключи.
В OnModelCreating:
var imageEntity = modelBuilder.Entity<Image>();
// every image has composite primary key
imageEntity.HasKey(image => new {image.DefectId, image.AssetId});
Возможно, этого (вместе с вашими виртуальными свойствами) достаточно, чтобы структура сущностей обнаружила ваши отношения, особенно первичные ключи и внешние ключи.Если нет, сообщите об этом в структуру организации:
// every image belongs to exactly one Defect, using foreign key
imageEntity.HasRequired(image => image.Defect)
.WithMany(defect => defect.Images)
.HasForeignKey(image => image.DefectId,
imageEntity.HasRequired(image => image.Asset)
.WithMany(asset => assert.Images)
.HasForeignKey(image => image.AssetId);