【问题标题】:Trying to understand deleting children entities in Entity Framework试图理解删除实体框架中的子实体
【发布时间】:2016-03-26 01:04:15
【问题描述】:

我试图理解为什么 Entity Framework 的工作方式与删除子实体的方式一样!

我有一个YogaSpace 对象/实体和一个名为YogaSpaceImage 的子实体。我想从YogaSpace 中删除YogaSpaceImage,所以这就是我要做的。

工作

yogaSpace.Images.Remove(yogaSpaceImage);

删除子实体!

public string RemoveImage(int id, int imageIdToDelete)
{
        YogaSpace yogaSpace = _yogaSpaceRepository.Find(id);

        // delete image
        foreach (YogaSpaceImage yogaSpaceImage in yogaSpace.Images.OrderBy(m => m.Ordering))
        {
            if (yogaSpaceImage.YogaSpaceImageId == imageIdToDelete)
            {
                // check first to see if the deleted image is the first (primary) image, then make the 2nd image the yogaspace thumbnail
                if (yogaSpaceImage.Ordering == 1)
                {
                    yogaSpace.SpaceThumbnail = yogaSpace.Images.First(m => m.Ordering == 2).ImageThumbnail;
                }
                yogaSpace.Images.Remove(yogaSpaceImage);
            }
        } 
     }

     myRepository.InsertOrUpdate(YogaSpace);
     myRepository.Save()
}

当我致电myRepo.Removed(YogaSpaceImage) 时,这确实有效。

public string RemoveImage(int id, int imageIdToDelete)
{
        YogaSpace yogaSpace = _yogaSpaceRepository.Find(id);

        // delete image
        foreach (YogaSpaceImage yogaSpaceImage in yogaSpace.Images.OrderBy(m => m.Ordering))
        {
            if (yogaSpaceImage.YogaSpaceImageId == imageIdToDelete)
            {
                // check first to see if the deleted image is the first (primary) image, then make the 2nd image the yogaspace thumbnail
                if (yogaSpaceImage.Ordering == 1)
                {
                    yogaSpace.SpaceThumbnail = yogaSpace.Images.First(m => m.Ordering == 2).ImageThumbnail;
                }

                _yogaSpaceRepository.Removed(yogaSpaceImage);  
            }
        } 
     }

     myRepository.Save()
}

这是 Removed()InsertOrUpdate() 在我的仓库中的样子。

public void InsertOrUpdate(YogaSpace yogaSpace)
{
        if (yogaSpace.YogaSpaceId == default(int))
        {
            context.Entry(yogaSpace).State = System.Data.Entity.EntityState.Added;
        }
        else
        {
            context.Entry(yogaSpace).State = System.Data.Entity.EntityState.Modified;
        }
}

public void Removed(YogaSpaceImage yogaSpaceImage)
{
        context.Entry(yogaSpaceImage).State = EntityState.Deleted;
}

附:你会认为我的仓库中的InsetOrUpdate() 可以为EntityState.Modified 删除子实体吗?

P.P.S.不知道为什么我什至需要InsertOrUpdate(),它是使用自动生成的 nuget 包构建的。如果我不使用它而只是调用Save(),实体框架会理解我所做的更改,那么为什么它会为我生成以及为什么entity.Addedentity.Modified 甚至存在,因为实体被保存并且即使我没有明确调用这两个也进行了修改?

【问题讨论】:

标签: c# entity-framework


【解决方案1】:

一个不错的小技巧是在孩子的主键中使用父母的 id:

public class Parent
{
    public int Id { get; set; }

    public virtual List<Child> Children { get; set; }
}

public class Child
{
    public int Id { get; set; }

    public int ParentId { get; set;}
}

以及配置:

modelBuilder.Entity<Parent>()
            .HasMany(x => x.Children)
            .WithRequired()
            .HasForeignKey(x => x.ParentId);

modelBuilder.Entity<Child>()
            .HasKey(x => new { x.Id, x.ParentId})
            .Property(x => x.Id)
            .HasDatabaseGeneratedOption(DatabaseGeneratedOption.Identity);

这样当你从父级中删除一个子级时,ParentId 不能为空,EF 会将子级标记为删除。

如何向父级添加/删除子级的示例:

using(var db = new DbContext())
{
    var p = db.Parents.First();
    var c = new Child();
    p.Children.Add(c);
    db.SaveChanges(); // Child was saved to the database

    p.Children.Remove(c);
    db.SaveChanges(); // Child will be deleted from the database

    p.Children.Clear();
    db.SaveChanges(); // All Child of this parent will be deleted
}

【讨论】:

  • 有没有办法用属性做到这一点?我没有使用您的系统(不记得名称)来定义关系和键。顺便说一句,我确实有父实体的 ref id。我在我的对象中定义它,例如 [Index] public int YogaSpaceRefId { get;放; }[ForeignKey("YogaSpaceRefId")] 公共虚拟 YogaSpace YogaSpace { get;放; } 和公共虚拟 ICollection 图像 { 获取;放; }
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2012-11-24
  • 2011-08-30
  • 1970-01-01
  • 1970-01-01
  • 2011-05-08
相关资源
最近更新 更多