EF 6.1.1 - 由于一个或多个外键属性不可为空,因此无法更改关系

时间:2014-11-18 16:55:57

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

尝试删除实体之间的关系并创建新实体时,我收到此错误。

public partial class Course
{
    public int Course_ID { get; set; }
    /* CODE*/
    public virtual ICollection<Student> Students { get; set; }
}

public partial class Student
{
    public int Student_ID { get; set; }
    /* CODE*/
    public virtual ICollection<Course> Courses { get; set; }
    public virtual ICollection<Book> Books { get; set; }
}

public partial class Book
{
    public int Book_ID { get; set; }
    public int Student_ID { get; set; }
    /* CODE*/
    public virtual Student Student { get; set; }
}

关系如下:

  • 课程* - *学生(学生和课程有多对多的关系,因此表格Student_Courses是在规范化过程中创建的 - 学生可以参与多个课程,课程有多个学生)
  • 学生1 - *预订(学生与书有一对多的关系 - 学生有很多书,一本书属于一个学生)

我正在尝试更新这样的学生实体:

    public bool UpdateEntity(Entities.Student student)
    {
        using (var context = new Entities())
        {
            var record = context.Students
                                .Include("Courses")
                                .Include("Books")
                                .FirstOrDefault(c => c.Student_ID == student.Student_ID );

            // record.Courses.ToList().ForEach(s => record.Courses.Remove(s));
            // record.Books.ToList().ForEach(t => record.Books.Remove(t));

            record.Courses.Clear();
            record.Books.Clear();

            record.Courses= student.Courses;
            record.Books= student.Books;
            context.SaveChanges();

            return true;
        }
    }

在不删除实际课程的情况下,应删除学生与课程之间的关系。 更新书籍和学生之间的关系时,也应删除该书。

修改 更新以使其更清晰

1 个答案:

答案 0 :(得分:1)

如果要从数据库中删除1-many集合中的项目,则必须将每个项目标记为要删除,例如像这样:

foreach (var book in record.Books)
{
    context.Books.Remove(book);
}
context.SaveChanges();

有时令人讨厌。当您Clear收集导航属性时,EF会谨慎行事并尝试仅在不删除项目的情况下中断关联,即尝试使外键无效。但是,EF 确实知道 FK字段在数据库中不可为空,所以在我看来,EF 能够弄清楚在这种情况下它是&#39用户删除项目的意图,而不是孤立他们的意图。但太糟糕了,它没有。

我曾经使用NHibernate和IIRC,NHibernate在类似的情况下确实删除了子项,甚至开了一次删除(delete from Child where Child.ParentId = ...)。 EF分别为每个孩子发布删除声明。

相关问题