Подтвердить что ты не робот

Были обнаружены конфликтующие изменения в роли x отношения y

У меня есть исключение

Были обнаружены конфликтующие изменения в роли x отношения y.

Каждый раз, когда я добавляю свой объект в свой контекст

Database.MyEntitys.Add(MyEntity);

Класс MyEntity содержит это свойство:

public virtual ICollection<DetailInfo> Group { get; set; }

Класс DetailInfo довольно прост:

public class DetailInfo:BaseEntity {
    public virtual Detail Detail { get; set; }
    public decimal Total { get; set; }
    public virtual MyEntity MyEntity { get; set; }
}

DatabaseContext также прост:

public class MyEntityConfiguration : EntityTypeConfiguration<MyEntity> {
    public MyEntityConfiguration() {
        HasMany(e => e.Group).WithRequired(s => s.MyEntity).WillCascadeOnDelete(true);
    }
}

public class DetailInfoConfiguration : EntityTypeConfiguration<DetailInfo> {
    public DetailInfoConfiguration() {
        HasRequired(x => x.MyEntity).WithMany(s => s.Group);
        HasRequired(x => x.Detail);
        HasKey(s => s.ID);
        ToTable("DetailInfo");
    }
}

В стороне базы данных таблица MyEntity имеет первичный ключ к идентификатору столбца. В DetailInfo также есть первичный ключ с идентификатором. DetailInfo содержит 2 FK, один для MyEntity и один для Detail, который является другим объектом.

В проблемном сценарии MyEntity имеет новый элемент Detail. Я ожидаю новую запись для MyEntity с новой деталью и правильную настройку FK.

Edit:

здесь находится Insert:

public virtual int Insert(MyEntity myEntity) {

    if (myEntity.Group != null && myEntity.Group.Count() == 0) {
        myEntity.Group = null; 
    }

    if (myEntity.Group != null) {
        foreach (var g in myEntity.Group)
        {
         if (g.PropertyOneToOne != null) {
                if (g.PropertyOneToOne.ID == 0) {
                    myEntity.PropertyOneToOne = null;
                }
                else {
                    if (!Database.PropertyOneToOnes.Local.Any(e => e.ID == g.PropertyOneToOne.ID)) {
                        Database.PropertyOneToOnes.Attach(g.PropertyOneToOne);
                    }
                    myEntity.PropertyOneToOne = Database.PropertyOneToOnes.Local.Single(e => e.ID == g.PropertyOneToOne.ID);
                }
            }
            else {
                myEntity.PropertyOneToOne = null;
            }
        }
    }
    Database.MyEntitys.Add(myEntity);
}
4b9b3361

Ответ 1

Проблема заключается в следующем:

MyEntity имеет идентификатор 0, так как это новый MyEntity. Группа также является новой и содержит ссылку на MyEntity.

Итак, MyEntity содержит список группы, содержащий ссылку на MyEntity.

Проблема заключается в том, что MyEntity.Group.MyEntity кажется "новым, а не тем же", что и MyEntity. При добавлении MyEntity к контексту он обнаружил конфликт.

Чтобы решить проблему, я установил Group.MyEntity в NULL и сохранил ссылку группы внутри списка MyEntity. При сохранении в таблицу групп устанавливается MyEntity reference (ID).

Я не уверен, что это самый чистый способ сделать это, но проблема окончательно решена.

Ответ 2

Некоторое другое решение может быть связано с необходимостью конфигурирования данных с привязкой к двум способам, поскольку для MyEntity необходимо, чтобы группа и группа имели MyEntity. Вы можете ссылаться на эту ссылку, чтобы настроить двустороннюю привязку. Надеюсь, поможет. EF 5.0 Code First Двусторонняя навигация с идентификатором внешнего ключа в дочерней машине

Ответ 3

Проблема также может заключаться в том, что вы создаете новый дочерний список, и вы назначаете этот список нескольким элементам родительского списка, решение состоит в том, что вы должны создать новый дочерний список для каждого из родительских элементов.