【问题标题】:Why can't I delete a nested entity object with EF and ASP.Net MVC为什么我不能使用 EF 和 ASP.Net MVC 删除嵌套实体对象
【发布时间】:2017-03-18 22:26:37
【问题描述】:

我有两个对象。配置文件和 ProfileImage。我的上下文设置为获取配置文件,我想通过配置文件删除 ProfileImage(不仅仅是引用),首先获取配置文件然后获取 profileImage 并像这样删除它:

using (var dbContext = new myContext())
        {
            var profile = dbContext.profiles.Where(i => i.ApplicationUserGuid == userId).First();

            var profileImageToDelete = profile.profileImages.Where(i => i.YogaProfileImageId == Convert.ToInt32(idToRemove)).First();

            profile.ProfileImages.Remove(profileImageToDelete);

            dbContext.SaveChanges();
        }

但保存时出现错误提示:

操作失败:无法更改关系,因为一个或多个外键属性不可为空。当对关系进行更改时,相关的外键属性将设置为空值。如果外键不支持空值,则必须定义新关系,必须为外键属性分配另一个非空值,或者必须删除不相关的对象。

这是我的两个实体对象:

public class Profile
{
    public Profile()
    {
        ProfileImages = new List<ProfileImage>();
    }

    [Key]
    public int ProfileId { get; set; }

    [Column(TypeName = "VARCHAR")]
    [StringLength(36)]
    [Index]
    public string ApplicationUserGuid { get; set; }

    public bool IsActive { get; set; }

    public virtual ICollection<ProfileImage> ProfileImages { get; set; } //one-to-many }


public class ProfileImage
{
    [Key]
    public int ProfileImageId { get; set; }
    public int ProfileRefId { get; set; }
    [ForeignKey("ProfileRefId")]
    public virtual Profile Profile { get; set; }
    public byte[] CroppedImage { get; set; }
    public byte[] ImageThumbnailCropped { get; set; }
    public bool IsMainImage { get; set; }
}

我读过一些关于级联删除的文章,但不确定这是我需要做的还是我需要做些什么才能让图像从 ProfileImage 表中完全删除。

【问题讨论】:

  • 那么你删除了一个项目,其他项目不应该引用它,或者应该适当设置级联规则。
  • 这是什么意思,如果有的话,我应该改变什么?
  • 嗯,由您决定是否适当地修复数据库设计或找出无法删除项目的原因...原因和解决方案因每个应用程序而异。有时,您可能想要删除指向该对象的任何对象。有时,您想设置一个空链接。有时,您想防止这种情况发生。有时,如果存在一些循环或复杂的逻辑,您可能必须在代码中手动执行此操作。 在您的情况下,您必须使用级联删除或您自己的代码从配置文件中删除图像,否则配置文件将具有不存在的图像。

标签: c# asp.net-mvc entity-framework cascading-deletes


【解决方案1】:

尝试添加:

dbContext.Entry(profileImageToDelete).State = EntityState.Deleted;

申请前dbContext.SaveChanges();

【讨论】:

【解决方案2】:

entitystatetracker 没有看到对您的 profileImage 进行的任何修改,因此从内存集合中删除此实体不会保存回数据库。

正如 Faisal 所提到的,您可以通过将实体状态设置为已删除,让 entitystatetracker 知道该对象应该从数据库中删除:

dbContext.Entry(profileImageToDelete).State = EntityState.Deleted;

但是,除了将其标记为已删除之外,您还可以使用:

dbContext.profileImages.Remove(profileImageToDelete);
dbContext.SaveChanges();

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2011-09-20
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多